* corrected terrain placement

* corrected object placement
* corrected grid formulas
* update MyCharacter position when beeing teleported
* tested in dun morogh, stormwind, thrallmar and arathi basin, object placement on the map is just fine now ;)
* cleanups not yet done, old unused funcs are still there
This commit is contained in:
false_genesis 2008-04-02 15:30:35 +00:00
parent cc5cf995fd
commit 6d5b8de2d5
7 changed files with 90 additions and 32 deletions

View File

@ -34,7 +34,7 @@ void DrawObject::_Init(void)
{ {
if(!cube && _obj->IsWorldObject()) // only world objects have coords and can be drawn if(!cube && _obj->IsWorldObject()) // only world objects have coords and can be drawn
{ {
cube = _smgr->addCubeSceneNode(10); cube = _smgr->addCubeSceneNode(2);
cube->setName("CUBE"); cube->setName("CUBE");
//cube->setPosition(irr::core::vector3di(100,100,100)); //cube->setPosition(irr::core::vector3di(100,100,100));
cube->setRotation(irr::core::vector3df(0,0,0)); cube->setRotation(irr::core::vector3df(0,0,0));
@ -63,13 +63,7 @@ void DrawObject::Draw(void)
if(cube) if(cube)
{ {
WorldPosition pos = ((WorldObject*)_obj)->GetPosition(); WorldPosition pos = ((WorldObject*)_obj)->GetPosition();
// TODO: these formulas are horribly wrong! FIXME ASAP! cube->setPosition(irr::core::vector3df(-pos.x,pos.z,-pos.y));
// they work best for ".tele dunmorogh"
float dx=pos.x * -5.0f - 26830.0f;
float dy=pos.z;
float dz=pos.y * -3.5f - 566.0f;
cube->setPosition(irr::core::vector3df(dx,dy,dz));
if(_obj->IsPlayer()) if(_obj->IsPlayer())
{ {
cube->getMaterial(0).DiffuseColor.set(255,255,0,0); cube->getMaterial(0).DiffuseColor.set(255,255,0,0);

View File

@ -36,6 +36,8 @@ enum DriverIDs
#define RAD_TO_DEG(x) ((x)/ANGLE_STEP) #define RAD_TO_DEG(x) ((x)/ANGLE_STEP)
#define RAD_FIX(x) ( (x)>(2*M_PI) ? ((x)-(2*M_PI)) : (x) ) #define RAD_FIX(x) ( (x)>(2*M_PI) ? ((x)-(2*M_PI)) : (x) )
#define DEG_FIX(x) ( (x)>360 ? ((x)-360) : (x) ) #define DEG_FIX(x) ( (x)>360 ? ((x)-360) : (x) )
#define IRR_TO_O(x) (DEG_TO_RAD(x) + ((M_PI*3.0f)/2.0f))
#define O_TO_IRR(x) (((M_PI/3.0f)*2.0f) - DEG_TO_RAD(x))
#define COORD_SCALE_VALUE_X 0.336f #define COORD_SCALE_VALUE_X 0.336f
#define COORD_SCALE_VALUE_Y 0.2f #define COORD_SCALE_VALUE_Y 0.2f

View File

@ -62,6 +62,7 @@ public:
void OnUpdate(s32); void OnUpdate(s32);
void UpdateTerrain(void); void UpdateTerrain(void);
void InitTerrain(void); void InitTerrain(void);
void RelocateCamera(void);
WorldPosition GetWorldPosition(void); WorldPosition GetWorldPosition(void);
void SetWorldPosition(WorldPosition); void SetWorldPosition(WorldPosition);
@ -76,6 +77,7 @@ private:
s32 mapsize, meshsize; s32 mapsize, meshsize;
f32 tilesize; f32 tilesize;
WorldSession *wsession; WorldSession *wsession;
World *world;
MapMgr *mapmgr; MapMgr *mapmgr;
IGUIStaticText *debugText; IGUIStaticText *debugText;
bool debugmode; bool debugmode;

View File

@ -20,7 +20,8 @@ SceneWorld::SceneWorld(PseuGUI *g) : Scene(g)
// store some pointers right now to prevent repeated ptr dereferencing later (speeds up code) // store some pointers right now to prevent repeated ptr dereferencing later (speeds up code)
gui = g; gui = g;
wsession = gui->GetInstance()->GetWSession(); wsession = gui->GetInstance()->GetWSession();
mapmgr = wsession->GetWorld()->GetMapMgr(); world = wsession->GetWorld();
mapmgr = world->GetMapMgr();
// TODO: hardcoded for now, make this adjustable later // TODO: hardcoded for now, make this adjustable later
float fogdist = 150; float fogdist = 150;
@ -51,6 +52,7 @@ SceneWorld::SceneWorld(PseuGUI *g) : Scene(g)
InitTerrain(); InitTerrain();
UpdateTerrain(); UpdateTerrain();
RelocateCamera();
DEBUG(logdebug("SceneWorld: Init done!")); DEBUG(logdebug("SceneWorld: Init done!"));
} }
@ -124,6 +126,9 @@ void SceneWorld::OnUpdate(s32 timediff)
} }
} }
if(camera->getPitch() < 270 && camera->getPitch() > 90)
camera->turnUp(90);
if(mouse_pressed_left || mouse_pressed_right) if(mouse_pressed_left || mouse_pressed_right)
{ {
//if(device->getCursorControl()->isVisible()) //if(device->getCursorControl()->isVisible())
@ -150,7 +155,8 @@ void SceneWorld::OnUpdate(s32 timediff)
} }
// camera height control // camera height control
if (eventrecv->mouse.wheel < 10) eventrecv->mouse.wheel = 10; if (eventrecv->mouse.wheel < 10)
eventrecv->mouse.wheel = 10;
camera->setHeight( eventrecv->mouse.wheel + terrain->getHeight(camera->getPosition()) ); camera->setHeight( eventrecv->mouse.wheel + terrain->getHeight(camera->getPosition()) );
WorldPosition wp = GetWorldPosition(); WorldPosition wp = GetWorldPosition();
@ -162,6 +168,7 @@ void SceneWorld::OnUpdate(s32 timediff)
str += camera->getPosition().Y; str += camera->getPosition().Y;
str += L","; str += L",";
str += camera->getPosition().Z; str += camera->getPosition().Z;
str += L"\n";
str += " ## HEAD: "; str += " ## HEAD: ";
str += DEG_TO_RAD(camera->getHeading()); str += DEG_TO_RAD(camera->getHeading());
str += L" Pos: "; str += L" Pos: ";
@ -194,12 +201,11 @@ void SceneWorld::InitTerrain(void)
return; return;
} }
mapsize = 8 * 16 * 3; // 9-1 height floats in 16 chunks per tile per axis in 3 MapTiles mapsize = (8 * 16 * 3) - 1; // 9-1 height floats in 16 chunks per tile per axis in 3 MapTiles
tilesize = UNITSIZE; tilesize = UNITSIZE;
meshsize = (s32)CHUNKSIZE*3; meshsize = (s32)CHUNKSIZE*3;
vector3df terrainPos(0.0f, 0.0f, 0.0f); // TODO: use PseuWoW's world coords here?
camera->setPosition(core::vector3df(mapsize*tilesize/2, 0, mapsize*tilesize/2) + terrainPos); //camera->setPosition(core::vector3df(mapsize*tilesize/2, 0, mapsize*tilesize/2) + terrainPos);
terrain = new ShTlTerrainSceneNode(smgr,mapsize,mapsize,tilesize,meshsize); terrain = new ShTlTerrainSceneNode(smgr,mapsize,mapsize,tilesize,meshsize);
terrain->drop(); terrain->drop();
@ -207,7 +213,7 @@ void SceneWorld::InitTerrain(void)
terrain->setMaterialTexture(0, driver->getTexture("data/misc/dirt_test.jpg")); terrain->setMaterialTexture(0, driver->getTexture("data/misc/dirt_test.jpg"));
terrain->setMaterialFlag(video::EMF_LIGHTING, true); terrain->setMaterialFlag(video::EMF_LIGHTING, true);
terrain->setMaterialFlag(video::EMF_FOG_ENABLE, true); terrain->setMaterialFlag(video::EMF_FOG_ENABLE, true);
terrain->setPosition(terrainPos);
} }
@ -302,8 +308,40 @@ void SceneWorld::UpdateTerrain(void)
terrain->setColor(i,j, video::SColor(255,r,g,b)); terrain->setColor(i,j, video::SColor(255,r,g,b));
} }
// to set the correct position of the terrain, we have to use the top-left tile's coords as terrain base pos
MapTile *maptile = mapmgr->GetNearTile(-1, -1);
if(maptile)
{
vector3df tpos;
tpos.X = -maptile->GetBaseX();
tpos.Y = 0; // height already managed when building up terrain
tpos.Z = -maptile->GetBaseY();
logdebug("SceneWorld: Setting position of terrain (x:%.2f y:%.2f z:%.2f)", tpos.X, tpos.Y, tpos.Z);
terrain->setPosition(tpos);
}
logdebug("SceneWorld: Smoothing terrain normals..."); logdebug("SceneWorld: Smoothing terrain normals...");
terrain->smoothNormals(); terrain->smoothNormals();
// TODO: check if camera should really be relocated -> in case we got teleported
// do NOT relocate camera if we moved around and triggered the map loading code by ourself!
RelocateCamera();
}
void SceneWorld::RelocateCamera(void)
{
MyCharacter *my = wsession->GetMyChar();
if(my)
{
logdebug("SceneWorld: Relocating camera to MyCharacter");
camera->setPosition(vector3df(-my->GetX(),my->GetZ(),-my->GetY()));
camera->turnLeft(camera->getHeading() - O_TO_IRR(my->GetO()));
}
else
{
logerror("SceneWorld: Relocating camera to MyCharacter - not found!");
}
} }
WorldPosition SceneWorld::GetWorldPosition(void) WorldPosition SceneWorld::GetWorldPosition(void)
@ -328,12 +366,13 @@ WorldPosition SceneWorld::GetWorldPosition(void)
float relx = cam.X * COORD_SCALE_VALUE_X + CHUNKSIZE; float relx = cam.X * COORD_SCALE_VALUE_X + CHUNKSIZE;
float rely = cam.Z * COORD_SCALE_VALUE_Y + CHUNKSIZE; float rely = cam.Z * COORD_SCALE_VALUE_Y + CHUNKSIZE;
float o = DEG_TO_RAD(camera->getHeading()) + ((M_PI*3.0f)/2.0f); float o = IRR_TO_O(camera->getHeading()) + ((M_PI*3.0f)/2.0f);
return WorldPosition(mapx - relx, mapy - rely, cam.Y, RAD_FIX(o) ); return WorldPosition(mapx - relx, mapy - rely, cam.Y, RAD_FIX(o) );
} }
void SceneWorld::SetWorldPosition(WorldPosition wp) void SceneWorld::SetWorldPosition(WorldPosition wp)
{ {
return;
UpdateTerrain(); UpdateTerrain();
vector3df cam; vector3df cam;
dimension2d<s32> tsize = terrain->getSize(); dimension2d<s32> tsize = terrain->getSize();
@ -346,7 +385,7 @@ void SceneWorld::SetWorldPosition(WorldPosition wp)
} }
cam.X = tile->GetBaseX() - wp.x + (tsize.Width * UNITSIZE); cam.X = tile->GetBaseX() - wp.x + (tsize.Width * UNITSIZE);
cam.Z = tile->GetBaseX() - wp.y + (tsize.Height * UNITSIZE); cam.Z = tile->GetBaseX() - wp.y + (tsize.Height * UNITSIZE);
float heading = RAD_TO_DEG(((M_PI*3.0f)/2.0f) - wp.o); float heading = O_TO_IRR(wp.o);
float heading_diff = camera->getHeading() - heading; float heading_diff = camera->getHeading() - heading;
//logdebug("Setting camera to x: %3f y: %3f z:%3f head: %3f", cam.X, cam.Y, cam.Z, heading); //logdebug("Setting camera to x: %3f y: %3f z:%3f head: %3f", cam.X, cam.Y, cam.Z, heading);
//camera->turnLeft(heading_diff); //camera->turnLeft(heading_diff);

View File

@ -3,6 +3,19 @@
#include "MapTile.h" #include "MapTile.h"
#include "MapMgr.h" #include "MapMgr.h"
void MakeMapFilename(char *fn, uint32 m, uint32 x, uint32 y)
{
sprintf(fn,"./data/maps/%u_%u_%u.adt",m,x,y);
}
bool TileExistsInFile(uint32 m, uint32 x, uint32 y)
{
char buf[50];
MakeMapFilename(buf,m,x,y);
return GetFileSize(buf);
}
MapMgr::MapMgr() MapMgr::MapMgr()
{ {
DEBUG(logdebug("Creating MapMgr with TILESIZE=%.3f CHUNKSIZE=%.3f UNITSIZE=%.3f",TILESIZE,CHUNKSIZE,UNITSIZE)); DEBUG(logdebug("Creating MapMgr with TILESIZE=%.3f CHUNKSIZE=%.3f UNITSIZE=%.3f",TILESIZE,CHUNKSIZE,UNITSIZE));
@ -69,15 +82,23 @@ void MapMgr::_LoadTile(uint32 gx, uint32 gy, uint32 m)
{ {
if(!_tiles->TileExists(gx,gy)) if(!_tiles->TileExists(gx,gy))
{ {
logerror("MAPMGR: Not loading MapTile (%u, %u) map %u, no entry in WDT tile map",gx,gy,m); if(TileExistsInFile(m,gx,gy))
return; {
logerror("MapMgr: Tile (%u, %u) exists not in WDT, but as file?!",gx,gy);
// continue loading...
}
else
{
logerror("MAPMGR: Not loading MapTile (%u, %u) map %u, no entry in WDT tile map",gx,gy,m);
return;
}
} }
if( !_tiles->GetTile(gx,gy) ) if( !_tiles->GetTile(gx,gy) )
{ {
ADTFile *adt = new ADTFile(); ADTFile *adt = new ADTFile();
char buf[300]; char buf[300];
sprintf(buf,"data/maps/%u_%u_%u.adt",m,gx,gy); MakeMapFilename(buf,m,gx,gy);
if(adt->Load(buf)) if(adt->Load(buf))
{ {
logdebug("MAPMGR: Loaded ADT '%s'",buf); logdebug("MAPMGR: Loaded ADT '%s'",buf);
@ -120,7 +141,7 @@ void MapMgr::_UnloadOldTiles(void)
MapTile *MapMgr::GetTile(uint32 xg, uint32 yg, bool forceLoad) MapTile *MapMgr::GetTile(uint32 xg, uint32 yg, bool forceLoad)
{ {
MapTile *tile = _tiles->GetTile(xg,yg); MapTile *tile = _tiles->GetTile(xg,yg);
if(!tile) if(!tile && forceLoad)
{ {
_LoadTile(xg,yg,_mapid); _LoadTile(xg,yg,_mapid);
tile = _tiles->GetTile(xg,yg); tile = _tiles->GetTile(xg,yg);
@ -145,7 +166,7 @@ uint32 MapMgr::GetGridCoord(float f)
GridCoordPair MapMgr::GetTransformGridCoordPair(float x, float y) GridCoordPair MapMgr::GetTransformGridCoordPair(float x, float y)
{ {
return GridCoordPair(GetGridCoord(x), GetGridCoord(y)); return GridCoordPair(GetGridCoord(y), GetGridCoord(x)); // yes, they are reversed. definitely.
} }
uint32 MapMgr::GetLoadedMapsCount(void) uint32 MapMgr::GetLoadedMapsCount(void)

View File

@ -919,10 +919,11 @@ void WorldSession::_HandleTelePortAckOpcode(WorldPacket& recvPacket)
SendWorldPacket(response); SendWorldPacket(response);
_world->UpdatePos(x,y); _world->UpdatePos(x,y);
_world->Update();
if(PseuGUI *gui = GetInstance()->GetGUI()) if(MyCharacter *my = GetMyChar())
{ {
gui->SetWorldPosition(WorldPosition(x,y,z,o)); my->SetPosition(x,y,z,o);
} }
if(GetInstance()->GetScripts()->ScriptExists("_onteleport")) if(GetInstance()->GetScripts()->ScriptExists("_onteleport"))
@ -947,8 +948,6 @@ void WorldSession::_HandleNewWorldOpcode(WorldPacket& recvPacket)
// else we had to do the following before: // else we had to do the following before:
// recvPacket >> tmapid >> tx >> ty >> tz >> to; // recvPacket >> tmapid >> tx >> ty >> tz >> to;
recvPacket >> mapid >> x >> y >> z >> o; recvPacket >> mapid >> x >> y >> z >> o;
if(GetMyChar())
GetMyChar()->ClearSpells(); // will be resent by server
// when getting teleported, the client sends CMSG_CANCEL_TRADE 2 times.. dont ask me why. // when getting teleported, the client sends CMSG_CANCEL_TRADE 2 times.. dont ask me why.
WorldPacket wp(CMSG_CANCEL_TRADE,8); WorldPacket wp(CMSG_CANCEL_TRADE,8);
@ -978,14 +977,14 @@ void WorldSession::_HandleNewWorldOpcode(WorldPacket& recvPacket)
_world->UpdatePos(x,y,mapid); _world->UpdatePos(x,y,mapid);
_world->Update(); _world->Update();
// TODO: need to switch to SCENESTATE_LOGINSCREEN here, and after everything is loaded, back to SCENESTATE_WORLD if(MyCharacter *my = GetMyChar())
if(PseuGUI *gui = GetInstance()->GetGUI())
{ {
//gui->SetSceneState(SCENESTATE_WORLD); my->ClearSpells(); // will be resent by server
// commented out, should be world scene anyway at this point... my->SetPosition(x,y,z,o,mapid);
gui->SetWorldPosition(WorldPosition(x,y,z,o));
} }
// TODO: need to switch to SCENESTATE_LOGINSCREEN here, and after everything is loaded, back to SCENESTATE_WORLD
if(GetInstance()->GetScripts()->ScriptExists("_onteleport")) if(GetInstance()->GetScripts()->ScriptExists("_onteleport"))
{ {
CmdSet Set; CmdSet Set;

View File

@ -24,8 +24,8 @@ void MapTile::ImportFromADT(ADTFile *adt)
for(uint32 ch=0; ch<CHUNKS_PER_TILE; ch++) for(uint32 ch=0; ch<CHUNKS_PER_TILE; ch++)
{ {
_chunks[ch].baseheight = adt->_chunks[ch].hdr.zbase; // ADT files store (x/z) as ground coords and (y) as the height! _chunks[ch].baseheight = adt->_chunks[ch].hdr.zbase; // ADT files store (x/z) as ground coords and (y) as the height!
_chunks[ch].basex = adt->_chunks[ch].hdr.ybase; // here converting it to (x/y) on ground and basehight as actual height. _chunks[ch].basex = adt->_chunks[ch].hdr.xbase; // here converting it to (x/y) on ground and basehight as actual height.
_chunks[ch].basey = adt->_chunks[ch].hdr.xbase; // strange coords they use... :S _chunks[ch].basey = adt->_chunks[ch].hdr.ybase; // strange coords they use... :S
uint32 fcnt=0, rcnt=0; uint32 fcnt=0, rcnt=0;
while(true) //9*9 + 8*8 while(true) //9*9 + 8*8
{ {
@ -128,3 +128,4 @@ void MapTile::DebugDumpToFile(void)
fprintf(fh, out.c_str()); fprintf(fh, out.c_str());
fclose(fh); fclose(fh);
} }