TOON: Walk animation improved

Smoothing direction changes. Still needs to be polished though.

svn-id: r54221
This commit is contained in:
Sylvain Dupont 2010-11-13 01:15:37 +00:00
parent 405fd0b5eb
commit 698f4c2b45
9 changed files with 99 additions and 19 deletions

View File

@ -79,11 +79,66 @@ Character::~Character(void) {
void Character::init() {
}
void Character::forceFacing( int32 facing ) {
debugC(4, kDebugCharacter, "forceFacing(%d)", facing);
_facing = facing;
}
void Character::setFacing(int32 facing) {
debugC(4, kDebugCharacter, "setFacing(%d)", facing);
if (facing == _facing)
return;
if (_blockingWalk) {
_flags |= 2;
int32 dir = 0;
_lastWalkTime = _vm->getSystem()->getMillis();
if ((_facing - facing + 8) % 8 > (facing - _facing + 8) % 8)
dir = 1;
else
dir = -1;
while (_facing != facing) {
int32 elapsedTime = _vm->getOldMilli() - _lastWalkTime;
while (elapsedTime > _vm->getTickLength() * 3 && _facing != facing) {
_facing += dir;
while (_facing >= 8)
_facing -= 8;
while (_facing < 0)
_facing += 8;
elapsedTime -= _vm->getTickLength() * 3;
_lastWalkTime = _vm->getOldMilli();
}
if (_currentPathNode == 0)
playStandingAnim();
else
playWalkAnim(0,0);
_vm->doFrame();
};
_flags &= ~2;
}
_facing = facing;
}
void Character::forcePosition(int32 x, int32 y) {
debugC(5, kDebugCharacter, "forcePosition(%d, %d)", x, y);
setPosition(x,y);
_finalX = x;
_finalY = y;
}
void Character::setPosition(int32 x, int32 y) {
debugC(5, kDebugCharacter, "setPosition(%d, %d)", x, y);
@ -128,11 +183,13 @@ bool Character::walkTo(int32 newPosX, int32 newPosY) {
_currentPathNodeCount = _vm->getPathFinding()->getPathNodeCount();
_currentPathNode = 0;
stopSpecialAnim();
_flags |= 0x1;
_lastWalkTime = _vm->getSystem()->getMillis();
_numPixelToWalk = 0;
_flags |= 0x1;
if (_blockingWalk) {
while ((_x != newPosX || _y != newPosY) && _currentPathNode < _currentPathNodeCount && !_vm->shouldQuitGame()) {
if (_currentPathNode < _currentPathNodeCount - 10) {
@ -143,6 +200,8 @@ bool Character::walkTo(int32 newPosX, int32 newPosY) {
playWalkAnim(0, 0);
}
// in 1/1000 pixels
_numPixelToWalk += _speed * (_vm->getSystem()->getMillis() - _lastWalkTime) * _scale / 1024;
_lastWalkTime = _vm->getSystem()->getMillis();

View File

@ -58,6 +58,7 @@ public:
virtual int32 getId();
virtual void setId(int32 id);
virtual void setFacing(int32 facing);
virtual void forceFacing(int32 facing);
virtual int32 getFacing();
virtual void setAnimScript(int32 animScriptId);
virtual void setSceneAnimationId(int32 sceneAnimationId);
@ -69,6 +70,7 @@ public:
virtual int32 getAnimFlag();
virtual void setAnimFlag(int32 flag);
virtual void setPosition(int32 x, int32 y);
virtual void forcePosition(int32 x, int32 y);
virtual int32 getX();
virtual int32 getY();
virtual int32 getFinalX();

View File

@ -48,11 +48,6 @@ bool CharacterDrew::setupPalette() {
return false;
}
void CharacterDrew::setFacing(int32 facing) {
debugC(4, kDebugCharacter, "setFacing(%d)", facing);
_facing = facing;
}
void CharacterDrew::setPosition(int32 x, int32 y) {
debugC(5, kDebugCharacter, "setPosition(%d, %d)", x, y);
@ -88,7 +83,6 @@ void CharacterDrew::playStandingAnim() {
_animationInstance->stopAnimation();
_animationInstance->setLooping(true);
//setVisible(true);
}
void CharacterDrew::playWalkAnim(int32 start, int32 end) {

View File

@ -38,7 +38,6 @@ public:
CharacterDrew(ToonEngine *vm);
virtual ~CharacterDrew();
bool setupPalette();
void setFacing(int32 facing);
void playStandingAnim();
void setPosition(int32 x, int32 y);
void update(int32 timeIncrement);

View File

@ -204,6 +204,33 @@ int32 PathFinding::findClosestWalkingPoint(int32 xx, int32 yy, int32 *fxx, int32
}
}
bool PathFinding::lineIsWalkable(int32 x, int32 y, int32 x2, int32 y2) {
uint32 bx = x << 16;
int32 dx = x2 - x;
uint32 by = y << 16;
int32 dy = y2 - y;
uint32 adx = abs(dx);
uint32 ady = abs(dy);
int32 t = 0;
if (adx <= ady)
t = ady;
else
t = adx;
int32 cdx = (dx << 16) / t;
int32 cdy = (dy << 16) / t;
int32 i = t;
while (i) {
if(!isWalkable(bx >> 16, by >> 16))
return false;
bx += cdx;
by += cdy;
i--;
}
return true;
}
int32 PathFinding::findPath(int32 x, int32 y, int32 destx, int32 desty) {
debugC(1, kDebugPath, "findPath(%d, %d, %d, %d)", x, y, destx, desty);
@ -212,6 +239,9 @@ int32 PathFinding::findPath(int32 x, int32 y, int32 destx, int32 desty) {
return true;
}
// first test direct line
//if(lineIsWalkable(x,y,destx,desty))
memset(_gridTemp , 0, _width * _height * sizeof(int32));
_heap->clear();
int32 curX = x;
@ -223,9 +253,6 @@ int32 PathFinding::findPath(int32 x, int32 y, int32 destx, int32 desty) {
_heap->push(curX, curY, abs(destx - x) + abs(desty - y));
int wei = 0;
// Strangerke - Commented (not used)
// byte *mask = _currentMask->getDataPtr();
while (_heap->_count) {
wei = 0;
_heap->pop(&curX, &curY, &curWeight);

View File

@ -62,6 +62,7 @@ public:
int32 findPath(int32 x, int32 y, int32 destX, int32 destY);
int32 findClosestWalkingPoint(int32 xx, int32 yy, int32 *fxx, int32 *fyy, int origX = -1, int origY = -1);
bool isWalkable(int32 x, int32 y);
bool lineIsWalkable(int32 x, int32 y, int32 x2, int32 y2);
void init(Picture *mask);
void resetBlockingRects();

View File

@ -222,7 +222,7 @@ bool EMCInterpreter::run(EMCState *script) {
static bool EMCDebug = false;
if (EMCDebug)
debugC(5, 0, "[0x%.08X] EMCInterpreter::%s([%d/%u])", instOffset * 2, _opcodes[opcode].desc, _parameter, (uint)_parameter);
//debug(0, "[0x%.08X] EMCInterpreter::%s([%d/%u])", instOffset, _opcodes[opcode].desc, _parameter, (uint)_parameter);
//printf( "[0x%.08X] EMCInterpreter::%s([%d/%u])\n", instOffset, _opcodes[opcode].desc, _parameter, (uint)_parameter);
(this->*(_opcodes[opcode].proc))(script);
}

View File

@ -242,7 +242,7 @@ int32 ScriptFunc::sys_Cmd_Dummy(EMCState *state) {
}
int32 ScriptFunc::sys_Cmd_Change_Actor_X_And_Y(EMCState *state) {
_vm->getDrew()->setPosition(stackPos(0), stackPos(1));
_vm->getDrew()->forcePosition(stackPos(0), stackPos(1));
return 0;
}
@ -347,7 +347,7 @@ int32 ScriptFunc::sys_Cmd_Set_Sack_Visible(EMCState *state) {
}
int32 ScriptFunc::sys_Cmd_Set_Actor_Facing(EMCState *state) {
_vm->getDrew()->setFacing(stackPos(0));
_vm->getDrew()->forceFacing(stackPos(0));
_vm->getDrew()->playStandingAnim();
return 0;
}
@ -649,14 +649,14 @@ int32 ScriptFunc::sys_Cmd_Set_Flux_Facing_Point(EMCState *state) {
}
int32 ScriptFunc::sys_Cmd_Set_Flux_Facing(EMCState *state) {
_vm->getFlux()->setFacing(stackPos(0));
_vm->getFlux()->forceFacing(stackPos(0));
_vm->getFlux()->playStandingAnim();
return 0;
}
int32 ScriptFunc::sys_Cmd_Set_Flux_Coords(EMCState *state) {
_vm->getFlux()->stopWalk();
_vm->getFlux()->setPosition(stackPos(0), stackPos(1));
_vm->getFlux()->forcePosition(stackPos(0), stackPos(1));
return 0;
}

View File

@ -489,8 +489,6 @@ void ToonEngine::doFrame() {
render();
int32 currentTimer = _system->getMillis();
// Strangerke - Commented (not used)
// int32 elapsedTime = currentTimer - _oldTimer;
update(currentTimer - _oldTimer);
_oldTimer = currentTimer;
@ -1183,7 +1181,7 @@ void ToonEngine::loadScene(int32 SceneId, bool forGameLoad) {
waitForScriptStep();
if (_gameState->_nextSpecialEnterX != -1 && _gameState->_nextSpecialEnterY != -1) {
_drew->setPosition(_gameState->_nextSpecialEnterX, _gameState->_nextSpecialEnterY);
_drew->forcePosition(_gameState->_nextSpecialEnterX, _gameState->_nextSpecialEnterY);
_gameState->_nextSpecialEnterX = -1;
_gameState->_nextSpecialEnterY = -1;
}