TWINE: convert the holomap releated code to be more like the original source release

This commit is contained in:
Martin Gerhardy 2023-01-17 06:55:26 +01:00
parent 15fc0d6a4e
commit aaa7645a52
10 changed files with 202 additions and 218 deletions

View File

@ -56,8 +56,9 @@ namespace TwinE {
#define HOLOMAP_RESET (HOLOMAP_VISITED | HOLOMAP_UNK3 | HOLOMAP_UNK4 | HOLOMAP_UNK5 | HOLOMAP_UNK6 | HOLOMAP_UNK7)
#define HOLOMAP_ACTIVE (HOLOMAP_CAN_FOCUS | HOLOMAP_ARROW)
static const float zDistanceHolomap = 9500.0f;
static const float ZOOM_BIG_HOLO = 9500.0f;
static const float zDistanceTrajectory = 5300.0f;
static const int SIZE_CURSOR = 20;
Holomap::Holomap(TwinEEngine *engine) : _engine(engine) {}
@ -157,17 +158,23 @@ void Holomap::computeCoorGlobe(Common::SeekableReadStream *holomapSurfaceStream)
const int32 rot = holomapSurfaceStream->readByte();
holomapSurfaceStream->seek(-1, SEEK_CUR);
for (int beta = 0; beta < LBAAngles::ANGLE_360; beta += LBAAngles::ANGLE_11_25) {
const int32 rotX = holomapSurfaceStream->readByte();
const IVec3 &rotVec = _engine->_renderer->getHolomapRotation(rotX, alpha, beta);
_holomapSurface[holomapSurfaceArrayIdx].x = rotVec.x;
_holomapSurface[holomapSurfaceArrayIdx].y = rotVec.y;
_holomapSurface[holomapSurfaceArrayIdx].z = rotVec.z;
const int32 normal = 1000 + holomapSurfaceStream->readByte() * 2;
const IVec3 &rotVec = _engine->_renderer->getHolomapRotation(normal, 0, alpha);
const IVec3 &rotVec2 = _engine->_renderer->getHolomapRotation(rotVec.x, 0, beta);
const IVec3 &rotVec3 = _engine->_renderer->worldRotatePoint(IVec3(rotVec2.x, rotVec.y, rotVec2.y));
_holomapSurface[holomapSurfaceArrayIdx].x = rotVec3.x;
_holomapSurface[holomapSurfaceArrayIdx].y = rotVec3.y;
_holomapSurface[holomapSurfaceArrayIdx].z = rotVec3.z;
++holomapSurfaceArrayIdx;
}
const IVec3 &rotVec = _engine->_renderer->getHolomapRotation(rot, alpha, 0);
_holomapSurface[holomapSurfaceArrayIdx].x = rotVec.x;
_holomapSurface[holomapSurfaceArrayIdx].y = rotVec.y;
_holomapSurface[holomapSurfaceArrayIdx].z = rotVec.z;
const int32 normal = 1000 + rot * 2;
const IVec3 &rotVec = _engine->_renderer->getHolomapRotation(normal, 0, alpha);
const IVec3 &rotVec2 = _engine->_renderer->getHolomapRotation(rotVec.x, 0, 0);
const IVec3 &rotVec3 = _engine->_renderer->worldRotatePoint(IVec3(rotVec2.x, rotVec.y, rotVec2.y));
_holomapSurface[holomapSurfaceArrayIdx].x = rotVec3.x;
_holomapSurface[holomapSurfaceArrayIdx].y = rotVec3.y;
_holomapSurface[holomapSurfaceArrayIdx].z = rotVec3.z;
++holomapSurfaceArrayIdx;
}
assert(holomapSurfaceStream->eos());
@ -202,7 +209,7 @@ void Holomap::computeGlobeProj() {
for (int32 alpha = -LBAAngles::ANGLE_90; alpha <= LBAAngles::ANGLE_90; alpha += LBAAngles::ANGLE_11_25) {
for (int32 beta = 0; beta < LBAAngles::ANGLE_11_25; ++beta) {
IVec3 *vec = &_holomapSurface[holomapSurfaceArrayIdx++];
const IVec3 &destPos = _engine->_renderer->getBaseRotationPosition(vec->x, vec->y, vec->z);
const IVec3 &destPos = _engine->_renderer->longWorldRot(vec->x, vec->y, vec->z);
if (alpha != LBAAngles::ANGLE_90) {
_holomapSort[holomapSortArrayIdx].z = (int16)destPos.z;
_holomapSort[holomapSortArrayIdx].projectedPosIdx = _projectedSurfaceIndex;
@ -214,7 +221,7 @@ void Holomap::computeGlobeProj() {
++_projectedSurfaceIndex;
}
IVec3 *vec = &_holomapSurface[holomapSurfaceArrayIdx++];
const IVec3 &destPos = _engine->_renderer->getBaseRotationPosition(vec->x, vec->y, vec->z);
const IVec3 &destPos = _engine->_renderer->longWorldRot(vec->x, vec->y, vec->z);
const IVec3 &projPos = _engine->_renderer->projectPositionOnScreen(destPos);
_projectedSurfacePositions[_projectedSurfaceIndex].x1 = projPos.x;
_projectedSurfacePositions[_projectedSurfaceIndex].y1 = projPos.y;
@ -283,8 +290,8 @@ void Holomap::drawHolomapText(int32 centerx, int32 top, const char *title) {
void Holomap::drawHoloObj(const IVec3 &angle, int32 x, int32 y) {
_engine->_renderer->setAngleCamera(x, y, 0);
const IVec3 &destPos = _engine->_renderer->getBaseRotationPosition(0, 0, 1000);
_engine->_renderer->setBaseTranslation(0, 0, 0);
const IVec3 &destPos = _engine->_renderer->longWorldRot(0, 0, 1000);
_engine->_renderer->setPosCamera(0, 0, 0);
_engine->_renderer->setBaseRotation(angle);
_engine->_renderer->setBaseRotationPos(0, 0, distance(zDistanceTrajectory));
_engine->_interface->resetClip();
@ -307,12 +314,12 @@ void Holomap::renderHolomapVehicle(uint &frameNumber, ActorMoveStruct &move, Ani
}
const Common::Rect rect(0, _engine->height() - 280, 200, _engine->height() - 1);
_engine->_renderer->setProjection(rect.width() / 2, _engine->height() - 80, 128, 900, 900);
_engine->_renderer->setCameraAngle(0, 0, 0, 60, 128, 0, distance(30000));
_engine->_renderer->setFollowCamera(0, 0, 0, 60, 128, 0, distance(30000));
_engine->_renderer->setLightVector(-60, 128, 0);
// background of the vehicle
_engine->_interface->drawFilledRect(rect, COLOR_BLACK);
Common::Rect dummy;
_engine->_renderer->renderIsoModel(0, 0, 0, LBAAngles::ANGLE_0, newAngle, LBAAngles::ANGLE_0, bodyData, dummy);
_engine->_renderer->affObjetIso(0, 0, 0, LBAAngles::ANGLE_0, newAngle, LBAAngles::ANGLE_0, bodyData, dummy);
_engine->copyBlockPhys(rect);
}
@ -339,7 +346,7 @@ void Holomap::drawHolomapTrajectory(int32 trajectoryIndex) {
const int32 cameraPosX = _engine->width() / 2 + 80;
const int32 cameraPosY = _engine->height() / 2;
_engine->_renderer->setProjection(cameraPosX, cameraPosY, 128, 1024, 1024);
_engine->_renderer->setCameraAngle(0, 0, 0, data->pos.x, data->pos.y, data->pos.z, distance(zDistanceTrajectory));
_engine->_renderer->setFollowCamera(0, 0, 0, data->pos.x, data->pos.y, data->pos.z, distance(zDistanceTrajectory));
constexpr TwineResource holomapImageRes(Resources::HQR_RESS_FILE, RESSHQR_HOLOIMG);
uint8 *holomapImagePtr = nullptr;
@ -385,7 +392,7 @@ void Holomap::drawHolomapTrajectory(int32 trajectoryIndex) {
// now render the holomap path
_engine->_renderer->setProjection(cameraPosX, cameraPosY, 128, 1024, 1024);
_engine->_renderer->setCameraAngle(0, 0, 0, data->pos.x, data->pos.y, data->pos.z, distance(zDistanceTrajectory));
_engine->_renderer->setFollowCamera(0, 0, 0, data->pos.x, data->pos.y, data->pos.z, distance(zDistanceTrajectory));
_engine->_renderer->setLightVector(data->pos.x, data->pos.y, 0);
// animate the path from point 1 to point 2 by rendering a point model on each position
@ -417,7 +424,7 @@ void Holomap::drawHolomapTrajectory(int32 trajectoryIndex) {
_engine->_screens->clearScreen();
_engine->setPalette(_engine->_screens->_paletteRGBA);
_engine->_gameState->initEngineProjections();
_engine->_gameState->init3DGame();
_engine->_interface->loadClip();
_engine->_text->initSceneTextBank();
@ -426,7 +433,7 @@ void Holomap::drawHolomapTrajectory(int32 trajectoryIndex) {
free(holomapImagePtr);
}
int32 Holomap::getNextHolomapLocation(int32 currentLocation, int32 dir) const {
int32 Holomap::searchNextArrow(int32 currentLocation, int32 dir) const {
const int32 idx = currentLocation;
for (int32 i = currentLocation + dir; i != idx; i += dir) {
if (i < 0) {
@ -441,41 +448,42 @@ int32 Holomap::getNextHolomapLocation(int32 currentLocation, int32 dir) const {
return -1;
}
void Holomap::renderLocations(int xRot, int yRot, int zRot, bool lower) {
void Holomap::drawListPos(int xRot, int yRot, int zRot, bool lower) {
int n = 0;
DrawListStruct drawListArray[NUM_LOCATIONS];
for (int locationIdx = 0; locationIdx < NUM_LOCATIONS; ++locationIdx) {
if ((_engine->_gameState->_holomapFlags[locationIdx] & HOLOMAP_CAN_FOCUS) || locationIdx == _engine->_scene->_currentSceneIdx) {
const Location &loc = _locations[locationIdx];
_engine->_renderer->setAngleCamera(loc.angleX, loc.angleY, 0);
const IVec3 &destPos = _engine->_renderer->getBaseRotationPosition(0, 0, loc.size + 1000);
const IVec3 &destPos2 = _engine->_renderer->getBaseRotationPosition(0, 0, 1500);
_engine->_renderer->setAngleCamera(xRot, yRot, zRot, true);
_engine->_renderer->setBaseRotationPos(0, 0, distance(zDistanceHolomap));
const IVec3 &destPos3 = _engine->_renderer->getBaseRotationPosition(destPos);
const IVec3 &destPos4 = _engine->_renderer->getBaseRotationPosition(destPos2);
bool visible;
if (lower) {
visible = destPos3.z <= destPos4.z;
} else {
visible = destPos4.z <= destPos3.z;
}
if (!visible) {
continue;
}
uint8 flags = _engine->_gameState->_holomapFlags[locationIdx] & HOLOMAP_ARROW;
if (locationIdx == _engine->_scene->_currentSceneIdx) {
flags |= 2u; // model type
}
DrawListStruct &drawList = drawListArray[n];
drawList.posValue = destPos3.z;
drawList.actorIdx = locationIdx;
drawList.type = flags;
drawList.x = destPos.x;
drawList.y = destPos.y;
drawList.z = destPos.z;
++n;
if (!(_engine->_gameState->_holomapFlags[locationIdx] & HOLOMAP_CAN_FOCUS) && locationIdx != _engine->_scene->_currentSceneIdx) {
continue;
}
const Location &loc = _locations[locationIdx];
_engine->_renderer->setAngleCamera(loc.angleX, loc.angleY, 0);
const IVec3 &destPos = _engine->_renderer->longWorldRot(0, 0, loc.size + 1000);
const IVec3 &destPos2 = _engine->_renderer->longWorldRot(0, 0, 1500);
_engine->_renderer->setInverseAngleCamera(xRot, yRot, zRot);
_engine->_renderer->setBaseRotationPos(0, 0, distance(ZOOM_BIG_HOLO));
const IVec3 &destPos3 = _engine->_renderer->worldRotatePoint(destPos);
const IVec3 &destPos4 = _engine->_renderer->worldRotatePoint(destPos2);
bool visible;
if (lower) {
visible = destPos3.z <= destPos4.z;
} else {
visible = destPos4.z <= destPos3.z;
}
if (!visible) {
continue;
}
uint8 flags = _engine->_gameState->_holomapFlags[locationIdx] & HOLOMAP_ARROW;
if (locationIdx == _engine->_scene->_currentSceneIdx) {
flags |= 2u; // model type
}
DrawListStruct &drawList = drawListArray[n];
drawList.posValue = destPos3.z;
drawList.actorIdx = locationIdx;
drawList.type = flags;
drawList.x = destPos.x;
drawList.y = destPos.y;
drawList.z = destPos.z;
++n;
}
_engine->_redraw->sortDrawingList(drawListArray, n);
for (int i = 0; i < n; ++i) {
@ -493,35 +501,35 @@ void Holomap::renderLocations(int xRot, int yRot, int zRot, bool lower) {
const int32 angleX = _locations[drawList.actorIdx].angleX;
const int32 angleY = _locations[drawList.actorIdx].angleY;
Common::Rect dummy;
_engine->_renderer->renderIsoModel(drawList.x, drawList.y, drawList.z, angleX, angleY, LBAAngles::ANGLE_0, *bodyData, dummy);
_engine->_renderer->affObjetIso(drawList.x, drawList.y, drawList.z, angleX, angleY, LBAAngles::ANGLE_0, *bodyData, dummy);
}
}
}
void Holomap::processHolomap() {
void Holomap::holoMap() {
ScopedEngineFreeze freeze(_engine);
const int32 alphaLightTmp = _engine->_scene->_alphaLight;
const int32 betaLightTmp = _engine->_scene->_betaLight;
_engine->exitSceneryView();
_engine->_gameState->initEngineProjections();
_engine->_gameState->init3DGame();
_engine->_screens->fadeToBlack(_engine->_screens->_paletteRGBA);
_engine->_sound->stopSamples();
_engine->_interface->saveClip();
_engine->_interface->resetClip();
_engine->_screens->clearScreen();
_engine->_screens->fadeToBlack(_engine->_screens->_paletteRGBA);
initHoloDatas();
_engine->_text->initDial(TextBankId::Inventory_Intro_and_Holomap);
_engine->_text->setFontCrossColor(COLOR_9);
const int32 cameraPosX = _engine->width() / 2;
const int32 cameraPosY = scale(190);
_engine->_renderer->setProjection(cameraPosX, cameraPosY, 128, 1024, 1024);
_engine->_text->initDial(TextBankId::Inventory_Intro_and_Holomap);
_engine->_text->setFontCrossColor(COLOR_9);
constexpr TwineResource holomapImageRes(Resources::HQR_RESS_FILE, RESSHQR_HOLOIMG);
uint8 *holomapImagePtr = nullptr;
const int32 holomapImageSize = HQR::getAllocEntry(&holomapImagePtr, holomapImageRes);
@ -548,7 +556,7 @@ void Holomap::processHolomap() {
}
if (_engine->_input->toggleActionIfActive(TwinEActionType::HolomapPrev)) {
const int32 nextLocation = getNextHolomapLocation(currentLocation, -1);
const int32 nextLocation = searchNextArrow(currentLocation, -1);
if (nextLocation != -1 && currentLocation != nextLocation) {
currentLocation = nextLocation;
_engine->_text->drawHolomapLocation(_locations[currentLocation].textIndex);
@ -556,7 +564,7 @@ void Holomap::processHolomap() {
automove = true;
}
} else if (_engine->_input->toggleActionIfActive(TwinEActionType::HolomapNext)) {
const int32 nextLocation = getNextHolomapLocation(currentLocation, 1);
const int32 nextLocation = searchNextArrow(currentLocation, 1);
if (nextLocation != -1 && currentLocation != nextLocation) {
currentLocation = nextLocation;
_engine->_text->drawHolomapLocation(_locations[currentLocation].textIndex);
@ -606,17 +614,17 @@ void Holomap::processHolomap() {
redraw = false;
const Common::Rect &rect = _engine->centerOnScreenX(scale(300), 0, scale(330));
_engine->_interface->drawFilledRect(rect, COLOR_BLACK);
_engine->_renderer->setAngleCamera(xRot, yRot, 0, true);
_engine->_renderer->setInverseAngleCamera(xRot, yRot, 0);
_engine->_renderer->setLightVector(xRot, yRot, 0);
renderLocations(xRot, yRot, 0, false);
_engine->_renderer->setAngleCamera(xRot, yRot, 0, true);
_engine->_renderer->setBaseRotationPos(0, 0, distance(zDistanceHolomap));
drawListPos(xRot, yRot, 0, false);
_engine->_renderer->setInverseAngleCamera(xRot, yRot, 0);
_engine->_renderer->setBaseRotationPos(0, 0, distance(ZOOM_BIG_HOLO));
drawHoloMap(holomapImagePtr, holomapImageSize);
renderLocations(xRot, yRot, 0, true);
drawListPos(xRot, yRot, 0, true);
drawHolomapText(_engine->width() / 2, 25, "HoloMap");
if (automove) {
// draw cursor
const Common::Rect &targetRect = _engine->centerOnScreen(40, 40);
const Common::Rect &targetRect = _engine->centerOnScreen(SIZE_CURSOR * 2, SIZE_CURSOR * 2);
_engine->_menu->drawRectBorders(targetRect.left, cameraPosY - 20, targetRect.right, cameraPosY + 20, 15, 15);
}
}
@ -639,7 +647,7 @@ void Holomap::processHolomap() {
_engine->_scene->_alphaLight = alphaLightTmp;
_engine->_scene->_betaLight = betaLightTmp;
_engine->_gameState->initEngineProjections();
_engine->_gameState->init3DGame();
_engine->_interface->loadClip();
_engine->_input->enableKeyMap(mainKeyMapId);

View File

@ -84,9 +84,9 @@ private:
uint8 _paletteHolomap[NUMOFCOLORS * 3]{0};
void drawHolomapText(int32 centerx, int32 top, const char *title);
int32 getNextHolomapLocation(int32 currentLocation, int32 dir) const;
int32 searchNextArrow(int32 currentLocation, int32 dir) const;
void renderLocations(int xRot, int yRot, int zRot, bool lower);
void drawListPos(int xRot, int yRot, int zRot, bool lower);
/**
* Renders a holomap path with single path points appearing slowly one after another
@ -129,7 +129,7 @@ public:
void initHoloDatas();
/** Main holomap process loop */
void processHolomap();
void holoMap();
};
} // namespace TwinE

View File

@ -1192,7 +1192,7 @@ void Menu::processBehaviourMenu(bool behaviourMenu) {
_engine->_lbaTime = tmpTime;
_engine->_gameState->initEngineProjections();
_engine->_gameState->init3DGame();
}
_engine->_actor->setBehaviour(_engine->_actor->_heroBehaviour);
@ -1216,7 +1216,7 @@ void Menu::drawItem(int32 left, int32 top, int32 item) {
if (item < NUM_INVENTORY_ITEMS && _engine->_gameState->hasItem((InventoryItems)item) && (!_engine->_gameState->inventoryDisabled() || item == InventoryItems::kiCloverLeaf)) {
_itemAngle[item] += LBAAngles::ANGLE_2;
_engine->_interface->setClip(rect);
_engine->_renderer->renderInventoryItem(itemX, itemY, _engine->_resources->_inventoryTable[item], _itemAngle[item], 15000);
_engine->_renderer->draw3dObject(itemX, itemY, _engine->_resources->_inventoryTable[item], _itemAngle[item], 15000);
_engine->_interface->resetClip();
if (item == InventoryItems::kGasItem) {
_engine->_text->setFontColor(COLOR_WHITE);
@ -1356,7 +1356,7 @@ void Menu::processInventoryMenu() {
_engine->_scene->_alphaLight = tmpAlphaLight;
_engine->_scene->_betaLight = tmpBetaLight;
_engine->_gameState->initEngineProjections();
_engine->_gameState->init3DGame();
_engine->_text->initSceneTextBank();

View File

@ -359,7 +359,7 @@ void Redraw::processDrawListActors(const DrawListStruct &drawCmd, bool bgRedraw)
}
}
if (!_engine->_renderer->renderIsoModel(delta.x, delta.y, delta.z, LBAAngles::ANGLE_0, actor->_beta, LBAAngles::ANGLE_0, _engine->_resources->_bodyData[actor->_body], renderRect)) {
if (!_engine->_renderer->affObjetIso(delta.x, delta.y, delta.z, LBAAngles::ANGLE_0, actor->_beta, LBAAngles::ANGLE_0, _engine->_resources->_bodyData[actor->_body], renderRect)) {
_engine->_interface->resetClip();
return;
}
@ -726,10 +726,10 @@ void Redraw::renderOverlays() {
const BodyData &bodyPtr = _engine->_resources->_inventoryTable[item];
_overlayRotation += 1; // overlayRotation += 8;
_engine->_renderer->renderInventoryItem(40, 40, bodyPtr, _overlayRotation, 16000);
_engine->_renderer->draw3dObject(40, 40, bodyPtr, _overlayRotation, 16000);
_engine->_menu->drawRectBorders(rect);
addRedrawArea(rect);
_engine->_gameState->initEngineProjections();
_engine->_gameState->init3DGame();
_engine->_interface->resetClip();
break;
}

View File

@ -65,16 +65,16 @@ IVec3 &Renderer::projectPositionOnScreen(int32 cX, int32 cY, int32 cZ) { // Proj
return _projPos;
}
if (_baseRotPos.z - cZ < 0) {
if (_cameraRot.z - cZ < 0) {
_projPos.x = 0;
_projPos.y = 0;
_projPos.z = 0;
return _projPos;
}
cX -= _baseRotPos.x;
cY -= _baseRotPos.y;
cZ = _baseRotPos.z - cZ;
cX -= _cameraRot.x;
cY -= _cameraRot.y;
cZ = _cameraRot.z - cZ;
int32 posZ = cZ + _kFactor;
if (posZ <= 0) {
@ -98,10 +98,10 @@ void Renderer::setProjection(int32 x, int32 y, int32 kfact, int32 lfactx, int32
_isUsingIsoProjection = false;
}
void Renderer::setBaseTranslation(int32 x, int32 y, int32 z) {
_baseTransPos.x = x;
_baseTransPos.y = y;
_baseTransPos.z = z;
void Renderer::setPosCamera(int32 x, int32 y, int32 z) {
_cameraPos.x = x;
_cameraPos.y = y;
_cameraPos.z = z;
}
void Renderer::setIsoProjection(int32 x, int32 y, int32 scale) {
@ -112,116 +112,92 @@ void Renderer::setIsoProjection(int32 x, int32 y, int32 scale) {
_isUsingIsoProjection = true;
}
void Renderer::baseMatrixTranspose() {
SWAP(_baseMatrix.row1.y, _baseMatrix.row2.x);
SWAP(_baseMatrix.row1.z, _baseMatrix.row3.x);
SWAP(_baseMatrix.row2.z, _baseMatrix.row3.y);
void Renderer::flipMatrix() {
SWAP(_matrixWorld.row1.y, _matrixWorld.row2.x);
SWAP(_matrixWorld.row1.z, _matrixWorld.row3.x);
SWAP(_matrixWorld.row2.z, _matrixWorld.row3.y);
}
IVec3 Renderer::setAngleCamera(int32 x, int32 y, int32 z, bool transpose) {
IVec3 Renderer::setInverseAngleCamera(int32 x, int32 y, int32 z) {
setAngleCamera(x, y, z);
flipMatrix();
_cameraRot = longWorldRot(_cameraPos.x, _cameraPos.y, _cameraPos.z);
return _cameraRot;
}
IVec3 Renderer::setAngleCamera(int32 x, int32 y, int32 z) {
const double Xradians = (double)((LBAAngles::ANGLE_90 - x) % LBAAngles::ANGLE_360) * 2 * M_PI / LBAAngles::ANGLE_360;
const double Yradians = (double)((LBAAngles::ANGLE_90 - y) % LBAAngles::ANGLE_360) * 2 * M_PI / LBAAngles::ANGLE_360;
const double Zradians = (double)((LBAAngles::ANGLE_90 - z) % LBAAngles::ANGLE_360) * 2 * M_PI / LBAAngles::ANGLE_360;
_baseMatrix.row1.x = (int32)(sin(Zradians) * sin(Yradians) * SCENE_SIZE_HALFF);
_baseMatrix.row1.y = (int32)(-cos(Zradians) * SCENE_SIZE_HALFF);
_baseMatrix.row1.z = (int32)(sin(Zradians) * cos(Yradians) * SCENE_SIZE_HALFF);
_baseMatrix.row2.x = (int32)(cos(Zradians) * sin(Xradians) * SCENE_SIZE_HALFF);
_baseMatrix.row2.y = (int32)(sin(Zradians) * sin(Xradians) * SCENE_SIZE_HALFF);
_baseMatrix.row3.x = (int32)(cos(Zradians) * cos(Xradians) * SCENE_SIZE_HALFF);
_baseMatrix.row3.y = (int32)(sin(Zradians) * cos(Xradians) * SCENE_SIZE_HALFF);
_matrixWorld.row1.x = (int32)(sin(Zradians) * sin(Yradians) * SCENE_SIZE_HALFF);
_matrixWorld.row1.y = (int32)(-cos(Zradians) * SCENE_SIZE_HALFF);
_matrixWorld.row1.z = (int32)(sin(Zradians) * cos(Yradians) * SCENE_SIZE_HALFF);
_matrixWorld.row2.x = (int32)(cos(Zradians) * sin(Xradians) * SCENE_SIZE_HALFF);
_matrixWorld.row2.y = (int32)(sin(Zradians) * sin(Xradians) * SCENE_SIZE_HALFF);
_matrixWorld.row3.x = (int32)(cos(Zradians) * cos(Xradians) * SCENE_SIZE_HALFF);
_matrixWorld.row3.y = (int32)(sin(Zradians) * cos(Xradians) * SCENE_SIZE_HALFF);
int32 matrixElem = _baseMatrix.row2.x;
int32 matrixElem = _matrixWorld.row2.x;
_baseMatrix.row2.x = (int32)(sin(Yradians) * matrixElem + SCENE_SIZE_HALFF * cos(Yradians) * cos(Xradians));
_baseMatrix.row2.z = (int32)(cos(Yradians) * matrixElem - SCENE_SIZE_HALFF * sin(Yradians) * cos(Xradians));
_matrixWorld.row2.x = (int32)(sin(Yradians) * matrixElem + SCENE_SIZE_HALFF * cos(Yradians) * cos(Xradians));
_matrixWorld.row2.z = (int32)(cos(Yradians) * matrixElem - SCENE_SIZE_HALFF * sin(Yradians) * cos(Xradians));
matrixElem = _baseMatrix.row3.x;
matrixElem = _matrixWorld.row3.x;
_baseMatrix.row3.x = (int32)(sin(Yradians) * matrixElem - SCENE_SIZE_HALFF * sin(Xradians) * cos(Yradians));
_baseMatrix.row3.z = (int32)(cos(Yradians) * matrixElem + SCENE_SIZE_HALFF * sin(Xradians) * sin(Yradians));
_matrixWorld.row3.x = (int32)(sin(Yradians) * matrixElem - SCENE_SIZE_HALFF * sin(Xradians) * cos(Yradians));
_matrixWorld.row3.z = (int32)(cos(Yradians) * matrixElem + SCENE_SIZE_HALFF * sin(Xradians) * sin(Yradians));
if (transpose) {
baseMatrixTranspose();
}
_baseRotPos = getBaseRotationPosition(_baseTransPos.x, _baseTransPos.y, _baseTransPos.z);
_cameraRot = longWorldRot(_cameraPos.x, _cameraPos.y, _cameraPos.z);
return _baseRotPos;
return _cameraRot;
}
IVec3 Renderer::getBaseRotationPosition(int32 x, int32 y, int32 z) {
const int32 vx = (_baseMatrix.row1.x * x + _baseMatrix.row1.y * y + _baseMatrix.row1.z * z) / SCENE_SIZE_HALF;
const int32 vy = (_baseMatrix.row2.x * x + _baseMatrix.row2.y * y + _baseMatrix.row2.z * z) / SCENE_SIZE_HALF;
const int32 vz = (_baseMatrix.row3.x * x + _baseMatrix.row3.y * y + _baseMatrix.row3.z * z) / SCENE_SIZE_HALF;
IVec3 Renderer::longWorldRot(int32 x, int32 y, int32 z) {
const int32 vx = (_matrixWorld.row1.x * x + _matrixWorld.row1.y * y + _matrixWorld.row1.z * z) / SCENE_SIZE_HALF;
const int32 vy = (_matrixWorld.row2.x * x + _matrixWorld.row2.y * y + _matrixWorld.row2.z * z) / SCENE_SIZE_HALF;
const int32 vz = (_matrixWorld.row3.x * x + _matrixWorld.row3.y * y + _matrixWorld.row3.z * z) / SCENE_SIZE_HALF;
return IVec3(vx, vy, vz);
}
IVec3 Renderer::getCameraAnglePositions(int32 x, int32 y, int32 z) {
const int32 vx = (_baseMatrix.row1.x * x + _baseMatrix.row2.x * y + _baseMatrix.row3.x * z) / SCENE_SIZE_HALF;
const int32 vy = (_baseMatrix.row1.y * x + _baseMatrix.row2.y * y + _baseMatrix.row3.y * z) / SCENE_SIZE_HALF;
const int32 vz = (_baseMatrix.row1.z * x + _baseMatrix.row2.z * y + _baseMatrix.row3.z * z) / SCENE_SIZE_HALF;
IVec3 Renderer::longInverseRot(int32 x, int32 y, int32 z) {
const int32 vx = (_matrixWorld.row1.x * x + _matrixWorld.row2.x * y + _matrixWorld.row3.x * z) / SCENE_SIZE_HALF;
const int32 vy = (_matrixWorld.row1.y * x + _matrixWorld.row2.y * y + _matrixWorld.row3.y * z) / SCENE_SIZE_HALF;
const int32 vz = (_matrixWorld.row1.z * x + _matrixWorld.row2.z * y + _matrixWorld.row3.z * z) / SCENE_SIZE_HALF;
return IVec3(vx, vy, vz);
}
IVec3 Renderer::translateGroup(const IMatrix3x3 &matrix, int32 x, int32 y, int32 z) {
IVec3 Renderer::rot(const IMatrix3x3 &matrix, int32 x, int32 y, int32 z) {
const int32 vx = (matrix.row1.x * x + matrix.row1.y * y + matrix.row1.z * z) / SCENE_SIZE_HALF;
const int32 vy = (matrix.row2.x * x + matrix.row2.y * y + matrix.row2.z * z) / SCENE_SIZE_HALF;
const int32 vz = (matrix.row3.x * x + matrix.row3.y * y + matrix.row3.z * z) / SCENE_SIZE_HALF;
return IVec3(vx, vy, vz);
}
void Renderer::setCameraAngle(int32 transPosX, int32 transPosY, int32 transPosZ, int32 rotPosX, int32 rotPosY, int32 rotPosZ, int32 param6) {
_baseTransPos.x = transPosX;
_baseTransPos.y = transPosY;
_baseTransPos.z = transPosZ;
void Renderer::setFollowCamera(int32 transPosX, int32 transPosY, int32 transPosZ, int32 cameraAlpha, int32 cameraBeta, int32 cameraGamma, int32 cameraZoom) {
_cameraPos.x = transPosX;
_cameraPos.y = transPosY;
_cameraPos.z = transPosZ;
setAngleCamera(rotPosX, rotPosY, rotPosZ);
setAngleCamera(cameraAlpha, cameraBeta, cameraGamma);
_cameraRot.z += cameraZoom;
_baseRotPos.z += param6;
_baseTransPos = updateCameraAnglePositions();
_cameraPos = longInverseRot(_cameraRot.x, _cameraRot.y, _cameraRot.z);
}
IVec3 Renderer::updateCameraAnglePositions(int zShift) {
return getCameraAnglePositions(_baseRotPos.x, _baseRotPos.y, _baseRotPos.z + zShift);
}
IVec3 Renderer::getHolomapRotation(const int32 x, const int32 y, const int32 angle) const {
if (angle) {
const int32 nSin = lba1ShadeAngleTable[ClampAngle(angle)];
const int32 nCos = lba1ShadeAngleTable[ClampAngle((angle + LBAAngles::ANGLE_90))];
IVec3 Renderer::getHolomapRotation(const int32 angleX, const int32 angleY, const int32 angleZ) const {
int32 rotX = angleX * 2 + 1000;
int32 rotY;
if (angleY == LBAAngles::ANGLE_0) {
rotY = LBAAngles::ANGLE_0;
} else {
rotY = -lba1ShadeAngleTable[ClampAngle(angleY)] * rotX / SCENE_SIZE_HALF;
rotX = lba1ShadeAngleTable[ClampAngle(angleY + LBAAngles::ANGLE_90)] * rotX / SCENE_SIZE_HALF;
const int32 x0 = ((x * nCos) + (y * nSin)) >> 14;
const int32 y0 = ((y * nCos) - (x * nSin)) >> 14;
return IVec3(x0, y0, 0);
}
int32 rotZ;
if (angleZ == LBAAngles::ANGLE_0) {
rotZ = LBAAngles::ANGLE_0;
} else {
rotZ = -lba1ShadeAngleTable[ClampAngle(angleZ)] * rotX / SCENE_SIZE_HALF;
rotX = lba1ShadeAngleTable[ClampAngle(angleZ + LBAAngles::ANGLE_90)] * rotX / SCENE_SIZE_HALF;
}
const int32 row1X = _baseMatrix.row1.x * rotX;
const int32 row1Y = _baseMatrix.row1.y * rotY;
const int32 row1Z = _baseMatrix.row1.z * rotZ;
const int32 row2X = _baseMatrix.row2.x * rotX;
const int32 row2Y = _baseMatrix.row2.y * rotY;
const int32 row2Z = _baseMatrix.row2.z * rotZ;
const int32 row3X = _baseMatrix.row3.x * rotX;
const int32 row3Y = _baseMatrix.row3.y * rotY;
const int32 row3Z = _baseMatrix.row3.z * rotZ;
IVec3 vec;
vec.x = (row1X + row1Y + row1Z) / SCENE_SIZE_HALF;
vec.y = (row2X + row2Y + row2Z) / SCENE_SIZE_HALF;
vec.z = (row3X + row3Y + row3Z) / SCENE_SIZE_HALF;
return vec;
return IVec3(x, y, 0);
}
void Renderer::applyRotation(IMatrix3x3 *targetMatrix, const IMatrix3x3 *currentMatrix, const IVec3 &angleVec) {
void Renderer::rotMatIndex2(IMatrix3x3 *targetMatrix, const IMatrix3x3 *currentMatrix, const IVec3 &angleVec) {
IMatrix3x3 matrix1;
IMatrix3x3 matrix2;
@ -316,7 +292,7 @@ void Renderer::processRotatedElement(IMatrix3x3 *targetMatrix, const Common::Arr
IVec3 destPos;
// if its the first point
if (bone.isRoot()) {
currentMatrix = &_baseMatrix;
currentMatrix = &_matrixWorld;
} else {
const int32 pointIdx = bone.vertex;
const int32 matrixIndex = bone.parent;
@ -326,7 +302,7 @@ void Renderer::processRotatedElement(IMatrix3x3 *targetMatrix, const Common::Arr
destPos = modelData->computedPoints[pointIdx];
}
applyRotation(targetMatrix, currentMatrix, renderAngle);
rotMatIndex2(targetMatrix, currentMatrix, renderAngle);
if (!numOfPoints) {
warning("RENDER WARNING: No points in this model!");
@ -359,7 +335,7 @@ void Renderer::processTranslatedElement(IMatrix3x3 *targetMatrix, const Common::
IVec3 destPos;
if (bone.isRoot()) { // base point
*targetMatrix = _baseMatrix;
*targetMatrix = _matrixWorld;
} else { // dependent
const int32 pointsIdx = bone.vertex;
destPos = modelData->computedPoints[pointsIdx];
@ -373,15 +349,11 @@ void Renderer::processTranslatedElement(IMatrix3x3 *targetMatrix, const Common::
}
void Renderer::setLightVector(int32 angleX, int32 angleY, int32 angleZ) {
// TODO: RECHECK THIS
/*_cameraAngleX = angleX;
_cameraAngleY = angleY;
_cameraAngleZ = angleZ;*/
const int32 normalUnit = 64;
const IVec3 renderAngle(angleX, angleY, angleZ);
IMatrix3x3 matrix;
applyRotation(&matrix, &_baseMatrix, renderAngle);
_lightNorm = translateGroup(matrix, 0, 0, normalUnit - 5);
rotMatIndex2(&matrix, &_matrixWorld, renderAngle);
_normalLight = rot(matrix, 0, 0, normalUnit - 5);
}
static FORCEINLINE int16 clamp(int16 x, int16 a, int16 b) {
@ -1820,7 +1792,7 @@ bool Renderer::renderAnimatedModel(ModelData *modelData, const BodyData &bodyDat
numNormals = bodyData.getBone(boneIdx).numNormals;
if (numNormals) {
const IMatrix3x3 matrix = *lightMatrix * _lightNorm;
const IMatrix3x3 matrix = *lightMatrix * _normalLight;
for (int32 i = 0; i < numNormals; ++i) { // for each normal
const BodyNormal &normalPtr = bodyData.getNormal(shadeIndex);
@ -1854,7 +1826,7 @@ bool Renderer::renderAnimatedModel(ModelData *modelData, const BodyData &bodyDat
return renderModelElements(numOfPrimitives, bodyData, &renderCmds, modelData, modelRect);
}
bool Renderer::renderIsoModel(int32 x, int32 y, int32 z, int32 angleX, int32 angleY, int32 angleZ, const BodyData &bodyData, Common::Rect &modelRect) {
bool Renderer::affObjetIso(int32 x, int32 y, int32 z, int32 angleX, int32 angleY, int32 angleZ, const BodyData &bodyData, Common::Rect &modelRect) {
IVec3 renderAngle;
renderAngle.x = angleX;
renderAngle.y = angleY;
@ -1872,7 +1844,7 @@ bool Renderer::renderIsoModel(int32 x, int32 y, int32 z, int32 angleX, int32 ang
renderPos.y = y;
renderPos.z = z;
} else {
renderPos = getBaseRotationPosition(x, y, z) - _baseRotPos;
renderPos = longWorldRot(x, y, z) - _cameraRot;
}
if (!bodyData.isAnimated()) {
@ -1913,19 +1885,19 @@ void Renderer::renderBehaviourModel(const Common::Rect &rect, int32 y, int32 ang
if (move.numOfStep == 0) {
_engine->_movements->initRealAngle(newAngle, newAngle - LBAAngles::ANGLE_90, LBAAngles::ANGLE_17, &move);
}
renderIsoModel(0, y, 0, LBAAngles::ANGLE_0, newAngle, LBAAngles::ANGLE_0, bodyData, dummy);
affObjetIso(0, y, 0, LBAAngles::ANGLE_0, newAngle, LBAAngles::ANGLE_0, bodyData, dummy);
} else {
renderIsoModel(0, y, 0, LBAAngles::ANGLE_0, angle, LBAAngles::ANGLE_0, bodyData, dummy);
affObjetIso(0, y, 0, LBAAngles::ANGLE_0, angle, LBAAngles::ANGLE_0, bodyData, dummy);
}
_engine->_interface->resetClip();
}
void Renderer::renderInventoryItem(int32 x, int32 y, const BodyData &bodyData, int32 angle, int32 param) {
void Renderer::draw3dObject(int32 x, int32 y, const BodyData &bodyData, int32 angle, int32 cameraZoom) {
setProjection(x, y, 128, 200, 200);
setCameraAngle(0, 0, 0, 60, 0, 0, param);
setFollowCamera(0, 0, 0, 60, 0, 0, cameraZoom);
Common::Rect dummy;
renderIsoModel(0, 0, 0, LBAAngles::ANGLE_0, angle, LBAAngles::ANGLE_0, bodyData, dummy);
affObjetIso(0, 0, 0, LBAAngles::ANGLE_0, angle, LBAAngles::ANGLE_0, bodyData, dummy);
}
void Renderer::fillHolomapTriangle(int16 *pDest, int32 x0, int32 y0, int32 x1, int32 y1) {

View File

@ -154,28 +154,28 @@ private:
bool renderAnimatedModel(ModelData *modelData, const BodyData &bodyData, RenderCommand *renderCmds, const IVec3 &angleVec, const IVec3 &renderPos, Common::Rect &modelRect);
bool computeSphere(int32 x, int32 y, int32 radius);
bool renderModelElements(int32 numOfPrimitives, const BodyData &bodyData, RenderCommand **renderCmds, ModelData *modelData, Common::Rect &modelRect);
IVec3 getCameraAnglePositions(int32 x, int32 y, int32 z);
IVec3 longInverseRot(int32 x, int32 y, int32 z);
inline IVec3 getCameraAnglePositions(const IVec3 &vec) {
return getCameraAnglePositions(vec.x, vec.y, vec.z);
return longInverseRot(vec.x, vec.y, vec.z);
}
void applyRotation(IMatrix3x3 *targetMatrix, const IMatrix3x3 *currentMatrix, const IVec3 &angleVec);
void rotMatIndex2(IMatrix3x3 *targetMatrix, const IMatrix3x3 *currentMatrix, const IVec3 &angleVec);
void applyPointsRotation(const Common::Array<BodyVertex>& vertices, int32 firstPoint, int32 numPoints, I16Vec3 *destPoints, const IMatrix3x3 *rotationMatrix, const IVec3 &destPos);
void processRotatedElement(IMatrix3x3 *targetMatrix, const Common::Array<BodyVertex>& vertices, int32 rotX, int32 rotY, int32 rotZ, const BodyBone &bone, ModelData *modelData);
void applyPointsTranslation(const Common::Array<BodyVertex>& vertices, int32 firstPoint, int32 numPoints, I16Vec3 *destPoints, const IMatrix3x3 *translationMatrix, const IVec3 &angleVec, const IVec3 &destPos);
void processTranslatedElement(IMatrix3x3 *targetMatrix, const Common::Array<BodyVertex>& vertices, int32 rotX, int32 rotY, int32 rotZ, const BodyBone &bone, ModelData *modelData);
IVec3 translateGroup(const IMatrix3x3 &matrix, int32 x, int32 y, int32 z);
IVec3 rot(const IMatrix3x3 &matrix, int32 x, int32 y, int32 z);
IVec3 _baseTransPos;
IVec3 _cameraPos;
IVec3 _projectionCenter{320, 200, 0};
int32 _kFactor = 128;
int32 _lFactorX = 1024;
int32 _lFactorY = 840;
IMatrix3x3 _baseMatrix;
IMatrix3x3 _matrixWorld;
IMatrix3x3 _matricesTable[30 + 1];
IVec3 _lightNorm;
IVec3 _baseRotPos;
IVec3 _normalLight; // NormalXLight
IVec3 _cameraRot;
RenderCommand _renderCmds[1000];
/**
@ -215,7 +215,7 @@ private:
uint8 *prepareSpheres(const Common::Array<BodySphere>& spheres, int32 &numOfPrimitives, RenderCommand **renderCmds, uint8 *renderBufferPtr, ModelData *modelData);
uint8 *prepareLines(const Common::Array<BodyLine>& lines, int32 &numOfPrimitives, RenderCommand **renderCmds, uint8 *renderBufferPtr, ModelData *modelData);
void baseMatrixTranspose();
void flipMatrix();
void renderHolomapPolygons(int32 top, int32 bottom, uint8 *holomapImage, uint32 holomapImageSize);
void fillHolomapTriangle(int16 *pDest, int32 x1, int32 y1, int32 x2, int32 y2);
@ -238,10 +238,10 @@ public:
IVec3 getHolomapRotation(const int32 angleX, const int32 angleY, const int32 angleZ) const;
void setLightVector(int32 angleX, int32 angleY, int32 angleZ);
IVec3 getBaseRotationPosition(int32 x, int32 y, int32 z);
IVec3 longWorldRot(int32 x, int32 y, int32 z);
inline IVec3 getBaseRotationPosition(const IVec3& vec) {
return getBaseRotationPosition(vec.x, vec.y, vec.z);
inline IVec3 worldRotatePoint(const IVec3& vec) {
return longWorldRot(vec.x, vec.y, vec.z);
}
void fillVertices(int vtop, int32 vsize, uint8 renderType, uint16 color);
@ -253,22 +253,22 @@ public:
IVec3 &projectPositionOnScreen(int32 cX, int32 cY, int32 cZ);
void setCameraAngle(int32 transPosX, int32 transPosY, int32 transPosZ, int32 rotPosX, int32 rotPosY, int32 rotPosZ, int32 param6);
IVec3 updateCameraAnglePositions(int zShift = 0);
void setBaseTranslation(int32 x, int32 y, int32 z);
IVec3 setAngleCamera(int32 x, int32 y, int32 z, bool transpose = false);
void setFollowCamera(int32 transPosX, int32 transPosY, int32 transPosZ, int32 cameraAlpha, int32 cameraBeta, int32 cameraGamma, int32 cameraZoom);
void setPosCamera(int32 x, int32 y, int32 z);
IVec3 setAngleCamera(int32 x, int32 y, int32 z);
IVec3 setInverseAngleCamera(int32 x, int32 y, int32 z);
inline IVec3 setBaseRotation(const IVec3 &rot, bool transpose = false) {
return setAngleCamera(rot.x, rot.y, rot.z, transpose);
inline IVec3 setBaseRotation(const IVec3 &rot) {
return setAngleCamera(rot.x, rot.y, rot.z);
}
void setProjection(int32 x, int32 y, int32 depthOffset, int32 scaleX, int32 scaleY);
void setIsoProjection(int32 x, int32 y, int32 scale);
bool renderIsoModel(int32 x, int32 y, int32 z, int32 angleX, int32 angleY, int32 angleZ, const BodyData &bodyData, Common::Rect &modelRect);
bool affObjetIso(int32 x, int32 y, int32 z, int32 angleX, int32 angleY, int32 angleZ, const BodyData &bodyData, Common::Rect &modelRect);
inline bool renderIsoModel(const IVec3 &pos, int32 angleX, int32 angleY, int32 angleZ, const BodyData &bodyData, Common::Rect &modelRect) {
return renderIsoModel(pos.x, pos.y, pos.z, angleX, angleY, angleZ, bodyData, modelRect);
return affObjetIso(pos.x, pos.y, pos.z, angleX, angleY, angleZ, bodyData, modelRect);
}
/**
@ -280,15 +280,18 @@ public:
*/
void renderBehaviourModel(const Common::Rect &rect, int32 y, int32 angle, const BodyData &bodyData, ActorMoveStruct &move);
void renderInventoryItem(int32 x, int32 y, const BodyData &bodyData, int32 angle, int32 param);
/**
* @brief Render an inventory item
*/
void draw3dObject(int32 x, int32 y, const BodyData &bodyData, int32 angle, int32 cameraZoom);
void renderHolomapVertices(const ComputedVertex vertexCoordinates[3], const ComputedVertex textureCoordinates[3], uint8 *holomapImage, uint32 holomapImageSize);
};
inline void Renderer::setBaseRotationPos(int32 x, int32 y, int32 z) {
_baseRotPos.x = x;
_baseRotPos.y = y;
_baseRotPos.z = z;
_cameraRot.x = x;
_cameraRot.y = y;
_cameraRot.z = z;
}
} // namespace TwinE

View File

@ -55,9 +55,9 @@ GameState::GameState(TwinEEngine *engine) : _engine(engine) {
Common::fill(&_gameChoices[0], &_gameChoices[10], TextId::kNone);
}
void GameState::initEngineProjections() {
_engine->_renderer->setIsoProjection(_engine->width() / 2 - 9, _engine->height() / 2, 512);
_engine->_renderer->setBaseTranslation(0, 0, 0);
void GameState::init3DGame() {
_engine->_renderer->setIsoProjection(_engine->width() / 2 - 8 - 1, _engine->height() / 2, SIZE_BRICK_XZ);
_engine->_renderer->setPosCamera(0, 0, 0);
_engine->_renderer->setAngleCamera(LBAAngles::ANGLE_0, LBAAngles::ANGLE_0, LBAAngles::ANGLE_0);
_engine->_renderer->setLightVector(_engine->_scene->_alphaLight, _engine->_scene->_betaLight, LBAAngles::ANGLE_0);
}
@ -106,7 +106,7 @@ void GameState::initEngineVars() {
_engine->_scene->_alphaLight = LBAAngles::ANGLE_315;
_engine->_scene->_betaLight = LBAAngles::ANGLE_334;
initEngineProjections();
init3DGame();
initGameStateVars();
initHeroVars();
@ -381,12 +381,12 @@ void GameState::doFoundObj(InventoryItems item) {
itemAngle += LBAAngles::ANGLE_2;
_engine->_renderer->renderInventoryItem(_engine->_renderer->_projPos.x, _engine->_renderer->_projPos.y, _engine->_resources->_inventoryTable[item], itemAngle, 10000);
_engine->_renderer->draw3dObject(_engine->_renderer->_projPos.x, _engine->_renderer->_projPos.y, _engine->_resources->_inventoryTable[item], itemAngle, 10000);
_engine->_menu->drawRectBorders(boxRect);
_engine->_redraw->addRedrawArea(boxRect);
_engine->_interface->resetClip();
initEngineProjections();
init3DGame();
if (_engine->_animations->setModelAnimation(currentAnimState, currentAnimData, bodyData, &_engine->_scene->_sceneHero->_animTimerData)) {
currentAnimState++; // keyframe
@ -438,7 +438,7 @@ void GameState::doFoundObj(InventoryItems item) {
}
}
initEngineProjections();
init3DGame();
_engine->_text->initSceneTextBank();
_engine->_text->stopVox(_engine->_text->_currDialTextEntry);
@ -502,6 +502,7 @@ void GameState::processGameoverAnimation() {
const Common::Rect &rect = _engine->centerOnScreen(_engine->width() / 2, _engine->height() / 2);
_engine->_interface->setClip(rect);
int32 zoom = 50000;
Common::Rect dummy;
while (!_engine->_input->toggleAbortAction() && (_engine->_lbaTime - startLbaTime) <= _engine->toSeconds(10)) {
FrameMarker frame(_engine, 66);
@ -510,26 +511,26 @@ void GameState::processGameoverAnimation() {
return;
}
const int32 zoom = _engine->_collision->clampedLerp(40000, 3200, _engine->toSeconds(10), _engine->_lbaTime - startLbaTime);
zoom = _engine->_collision->clampedLerp(40000, 3200, _engine->toSeconds(10), _engine->_lbaTime - startLbaTime);
const int32 angle = _engine->_screens->lerp(1, LBAAngles::ANGLE_360, _engine->toSeconds(2), (_engine->_lbaTime - startLbaTime) % _engine->toSeconds(2));
_engine->blitWorkToFront(rect);
_engine->_renderer->setCameraAngle(0, 0, 0, 0, -angle, 0, zoom);
_engine->_renderer->renderIsoModel(0, 0, 0, LBAAngles::ANGLE_0, LBAAngles::ANGLE_0, LBAAngles::ANGLE_0, gameOverPtr, dummy);
_engine->_renderer->setFollowCamera(0, 0, 0, 0, -angle, 0, zoom);
_engine->_renderer->affObjetIso(0, 0, 0, LBAAngles::ANGLE_0, LBAAngles::ANGLE_0, LBAAngles::ANGLE_0, gameOverPtr, dummy);
_engine->_lbaTime++;
}
_engine->_sound->playSample(Samples::Explode);
_engine->blitWorkToFront(rect);
_engine->_renderer->setCameraAngle(0, 0, 0, 0, 0, 0, 3200);
_engine->_renderer->renderIsoModel(0, 0, 0, LBAAngles::ANGLE_0, LBAAngles::ANGLE_0, LBAAngles::ANGLE_0, gameOverPtr, dummy);
_engine->_renderer->setFollowCamera(0, 0, 0, 0, 0, 0, zoom);
_engine->_renderer->affObjetIso(0, 0, 0, LBAAngles::ANGLE_0, LBAAngles::ANGLE_0, LBAAngles::ANGLE_0, gameOverPtr, dummy);
_engine->delaySkip(2000);
_engine->_interface->resetClip();
_engine->restoreFrontBuffer();
initEngineProjections();
init3DGame();
_engine->_lbaTime = tmpLbaTime;
}

View File

@ -188,7 +188,7 @@ public:
void initEngineVars();
/** Initialize engine 3D projections */
void initEngineProjections();
void init3DGame();
void doFoundObj(InventoryItems item);

View File

@ -2024,7 +2024,7 @@ int32 ScriptLife::lPLAY_CD_TRACK(TwinEEngine *engine, LifeScriptContext &ctx) {
*/
int32 ScriptLife::lPROJ_ISO(TwinEEngine *engine, LifeScriptContext &ctx) {
debugC(3, kDebugLevels::kDebugScripts, "LIFE::PROJ_ISO()");
engine->_gameState->initEngineProjections();
engine->_gameState->init3DGame();
return 0;
}
@ -2039,7 +2039,7 @@ int32 ScriptLife::lPROJ_3D(TwinEEngine *engine, LifeScriptContext &ctx) {
engine->_scene->_enableGridTileRendering = false;
engine->_renderer->setProjection(engine->width() / 2, engine->height() / 2, 128, 1024, 1024);
engine->_renderer->setCameraAngle(0, 1500, 0, 25, -128, 0, 13000);
engine->_renderer->setFollowCamera(0, 1500, 0, 25, -128, 0, 13000);
engine->_renderer->setLightVector(LBAAngles::ANGLE_315, LBAAngles::ANGLE_334, LBAAngles::ANGLE_0);
engine->_text->initDial(TextBankId::Credits);

View File

@ -684,7 +684,7 @@ void TwinEEngine::processInventoryAction() {
switch (_loopInventoryItem) {
case kiHolomap:
_holomap->processHolomap();
_holomap->holoMap();
_screens->_fadePalette = true;
break;
case kiMagicBall:
@ -898,7 +898,7 @@ bool TwinEEngine::runGameEngine() { // mainLoopInteration
// Draw holomap
if (_input->toggleActionIfActive(TwinEActionType::OpenHolomap) && _gameState->hasItem(InventoryItems::kiHolomap) && !_gameState->inventoryDisabled()) {
_holomap->processHolomap();
_holomap->holoMap();
_screens->_fadePalette = true;
_redraw->redrawEngineActions(true);
}