2016-01-04 12:17:30 +00:00
|
|
|
//
|
2016-01-12 03:41:44 +00:00
|
|
|
// Created by koncord on 04.01.16.
|
2016-01-04 12:17:30 +00:00
|
|
|
//
|
|
|
|
|
2016-01-12 03:41:44 +00:00
|
|
|
#include <stdexcept>
|
|
|
|
#include <iostream>
|
|
|
|
#include <string>
|
|
|
|
#include <components/esm/cellid.hpp>
|
2016-10-24 14:52:19 +00:00
|
|
|
|
2016-11-17 15:16:25 +00:00
|
|
|
#include "../mwbase/world.hpp"
|
|
|
|
#include "../mwbase/environment.hpp"
|
|
|
|
#include "../mwbase/mechanicsmanager.hpp"
|
|
|
|
#include "../mwbase/windowmanager.hpp"
|
|
|
|
|
|
|
|
#include "../mwworld/cellstore.hpp"
|
|
|
|
#include "../mwworld/esmstore.hpp"
|
|
|
|
#include "../mwworld/inventorystore.hpp"
|
|
|
|
|
|
|
|
#include "../mwclass/npc.hpp"
|
|
|
|
#include "../mwmechanics/npcstats.hpp"
|
|
|
|
#include "../mwmechanics/combat.hpp"
|
2016-10-24 14:52:19 +00:00
|
|
|
|
2016-08-04 16:31:15 +00:00
|
|
|
#include <SDL_messagebox.h>
|
2016-01-04 12:17:30 +00:00
|
|
|
#include "Networking.hpp"
|
|
|
|
#include "../mwstate/statemanagerimp.hpp"
|
2016-08-18 17:20:17 +00:00
|
|
|
#include <components/openmw-mp/Log.hpp>
|
2016-08-27 07:36:22 +00:00
|
|
|
#include <components/openmw-mp/Version.hpp>
|
2016-10-20 11:28:19 +00:00
|
|
|
#include <components/openmw-mp/Base/WorldEvent.hpp>
|
2016-01-12 03:41:44 +00:00
|
|
|
#include "DedicatedPlayer.hpp"
|
|
|
|
#include "Main.hpp"
|
2016-01-04 12:17:30 +00:00
|
|
|
|
|
|
|
using namespace std;
|
2016-01-12 03:41:44 +00:00
|
|
|
using namespace mwmp;
|
2016-01-04 12:17:30 +00:00
|
|
|
|
2016-10-19 19:49:35 +00:00
|
|
|
Networking::Networking(): peer(RakNet::RakPeerInterface::GetInstance()), playerController(peer), worldController(peer)
|
2016-01-04 12:17:30 +00:00
|
|
|
{
|
2016-01-12 03:41:44 +00:00
|
|
|
|
|
|
|
RakNet::SocketDescriptor sd;
|
|
|
|
sd.port=0;
|
|
|
|
RakNet::StartupResult b = peer->Startup(1,&sd, 1);
|
|
|
|
RakAssert(b==RAKNET_STARTED);
|
|
|
|
|
2016-10-19 19:49:35 +00:00
|
|
|
playerController.SetStream(0, &bsOut);
|
|
|
|
worldController.SetStream(0, &bsOut);
|
|
|
|
|
2016-01-12 03:41:44 +00:00
|
|
|
connected = 0;
|
2016-01-04 12:17:30 +00:00
|
|
|
}
|
|
|
|
|
2016-01-12 03:41:44 +00:00
|
|
|
Networking::~Networking()
|
2016-01-04 12:17:30 +00:00
|
|
|
{
|
2016-01-12 03:41:44 +00:00
|
|
|
peer->Shutdown(100);
|
|
|
|
peer->CloseConnection(peer->GetSystemAddressFromIndex(0), true, 0);
|
|
|
|
RakNet::RakPeerInterface::DestroyInstance(peer);
|
2016-01-04 12:17:30 +00:00
|
|
|
}
|
|
|
|
|
2016-11-15 19:54:06 +00:00
|
|
|
void Networking::update()
|
2016-01-04 12:17:30 +00:00
|
|
|
{
|
2016-01-12 03:41:44 +00:00
|
|
|
RakNet::Packet *packet;
|
2016-08-24 23:58:03 +00:00
|
|
|
std::string errmsg = "";
|
|
|
|
|
2016-01-12 03:41:44 +00:00
|
|
|
for (packet=peer->Receive(); packet; peer->DeallocatePacket(packet), packet=peer->Receive())
|
|
|
|
{
|
|
|
|
switch (packet->data[0])
|
|
|
|
{
|
|
|
|
case ID_REMOTE_DISCONNECTION_NOTIFICATION:
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_INFO, "Another client has disconnected.");
|
2016-01-12 03:41:44 +00:00
|
|
|
break;
|
|
|
|
case ID_REMOTE_CONNECTION_LOST:
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_INFO, "Another client has lost connection.");
|
2016-01-12 03:41:44 +00:00
|
|
|
break;
|
|
|
|
case ID_REMOTE_NEW_INCOMING_CONNECTION:
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_INFO, "Another client has connected.");
|
2016-01-12 03:41:44 +00:00
|
|
|
break;
|
|
|
|
case ID_CONNECTION_REQUEST_ACCEPTED:
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Our connection request has been accepted.");
|
2016-01-12 03:41:44 +00:00
|
|
|
break;
|
|
|
|
case ID_NEW_INCOMING_CONNECTION:
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_INFO, "A connection is incoming.");
|
2016-01-12 03:41:44 +00:00
|
|
|
break;
|
|
|
|
case ID_NO_FREE_INCOMING_CONNECTIONS:
|
2016-08-24 23:58:03 +00:00
|
|
|
errmsg = "The server is full.";
|
2016-01-12 03:41:44 +00:00
|
|
|
break;
|
|
|
|
case ID_DISCONNECTION_NOTIFICATION:
|
2016-08-24 23:58:03 +00:00
|
|
|
errmsg = "We have been disconnected.";
|
2016-01-12 03:41:44 +00:00
|
|
|
break;
|
|
|
|
case ID_CONNECTION_LOST:
|
2016-08-24 23:58:03 +00:00
|
|
|
errmsg = "Connection lost.";
|
2016-01-12 03:41:44 +00:00
|
|
|
break;
|
|
|
|
default:
|
2016-11-15 19:54:06 +00:00
|
|
|
receiveMessage(packet);
|
2016-08-19 04:54:10 +00:00
|
|
|
//LOG_MESSAGE_SIMPLE(Log::LOG_INFO, "Message with identifier %i has arrived.", packet->data[0]);
|
2016-01-12 03:41:44 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
2016-08-24 23:58:03 +00:00
|
|
|
|
2016-09-28 11:27:35 +00:00
|
|
|
if (!errmsg.empty())
|
|
|
|
{
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_ERROR, errmsg.c_str());
|
2016-08-24 23:58:03 +00:00
|
|
|
SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_ERROR, "tes3mp", errmsg.c_str(), 0);
|
|
|
|
MWBase::Environment::get().getStateManager()->requestQuit();
|
|
|
|
}
|
2016-01-04 12:17:30 +00:00
|
|
|
}
|
|
|
|
|
2016-11-15 19:54:06 +00:00
|
|
|
void Networking::sendData(RakNet::BitStream *bs)
|
2016-01-04 12:17:30 +00:00
|
|
|
{
|
2016-01-12 03:41:44 +00:00
|
|
|
peer->Send(bs, HIGH_PRIORITY, RELIABLE_ORDERED, 0, serverAddr, false);
|
2016-01-04 12:17:30 +00:00
|
|
|
}
|
|
|
|
|
2016-11-15 19:54:06 +00:00
|
|
|
void Networking::connect(const std::string &ip, unsigned short port)
|
2016-01-04 12:17:30 +00:00
|
|
|
{
|
2016-01-12 03:41:44 +00:00
|
|
|
RakNet::SystemAddress master;
|
|
|
|
master.SetBinaryAddress(ip.c_str());
|
|
|
|
master.SetPortHostOrder(port);
|
2016-08-09 10:25:52 +00:00
|
|
|
std::string errmsg = "";
|
2016-01-12 03:41:44 +00:00
|
|
|
|
2016-09-18 03:49:30 +00:00
|
|
|
stringstream sstr(TES3MP_VERSION);
|
|
|
|
sstr << TES3MP_PROTO_VERSION;
|
|
|
|
|
|
|
|
if (peer->Connect(master.ToString(false), master.GetPort(), sstr.str().c_str(), (int) sstr.str().size(), 0, 0, 3, 500, 0) != RakNet::CONNECTION_ATTEMPT_STARTED)
|
2016-08-09 10:25:52 +00:00
|
|
|
errmsg = "Connection attempt failed.\n";
|
2016-01-12 03:41:44 +00:00
|
|
|
|
|
|
|
bool queue = true;
|
2016-08-17 15:20:36 +00:00
|
|
|
while (queue)
|
2016-01-04 12:17:30 +00:00
|
|
|
{
|
2016-01-12 03:41:44 +00:00
|
|
|
for (RakNet::Packet *packet = peer->Receive(); packet; peer->DeallocatePacket(
|
|
|
|
packet), packet = peer->Receive())
|
|
|
|
{
|
|
|
|
switch (packet->data[0])
|
|
|
|
{
|
|
|
|
case ID_CONNECTION_ATTEMPT_FAILED:
|
|
|
|
{
|
2016-08-04 16:31:15 +00:00
|
|
|
errmsg = "Connection failed.\n"
|
2016-08-24 23:58:03 +00:00
|
|
|
"Either the IP address is wrong or a firewall on either system is blocking\n"
|
2016-08-04 16:31:15 +00:00
|
|
|
"UDP packets on the port you have chosen.";
|
2016-01-12 03:41:44 +00:00
|
|
|
queue = false;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_INVALID_PASSWORD:
|
|
|
|
{
|
2016-08-04 16:31:15 +00:00
|
|
|
errmsg = "Connection failed.\n"
|
2016-09-28 05:26:18 +00:00
|
|
|
"The client or server is outdated.";
|
2016-01-12 03:41:44 +00:00
|
|
|
queue = false;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_CONNECTION_REQUEST_ACCEPTED:
|
|
|
|
{
|
|
|
|
serverAddr = packet->systemAddress;
|
|
|
|
connected = true;
|
|
|
|
queue = false;
|
2016-01-04 12:17:30 +00:00
|
|
|
|
2016-08-19 04:54:10 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Received ID_CONNECTION_REQUESTED_ACCEPTED from %s",
|
2016-08-18 19:29:54 +00:00
|
|
|
serverAddr.ToString());
|
|
|
|
|
2016-01-12 03:41:44 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_DISCONNECTION_NOTIFICATION:
|
|
|
|
throw runtime_error("ID_DISCONNECTION_NOTIFICATION.\n");
|
|
|
|
case ID_CONNECTION_BANNED:
|
|
|
|
throw runtime_error("ID_CONNECTION_BANNED.\n");
|
|
|
|
case ID_CONNECTION_LOST:
|
|
|
|
throw runtime_error("ID_CONNECTION_LOST.\n");
|
|
|
|
default:
|
2016-08-19 04:54:10 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_INFO, "Connection message with identifier %i has arrived in initialization.", packet->data[0]);
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
|
|
|
}
|
2016-01-04 12:17:30 +00:00
|
|
|
}
|
2016-08-09 10:25:52 +00:00
|
|
|
|
2016-08-17 15:04:35 +00:00
|
|
|
if (!errmsg.empty())
|
2016-08-09 10:25:52 +00:00
|
|
|
{
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_ERROR, errmsg.c_str());
|
2016-08-24 23:58:03 +00:00
|
|
|
SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_ERROR, "tes3mp", errmsg.c_str(), 0);
|
2016-08-09 10:25:52 +00:00
|
|
|
MWBase::Environment::get().getStateManager()->requestQuit();
|
|
|
|
}
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
|
|
|
|
2016-11-15 19:54:06 +00:00
|
|
|
void Networking::processPlayerPacket(RakNet::Packet *packet)
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-10-26 12:55:34 +00:00
|
|
|
RakNet::RakNetGUID guid;
|
2016-08-05 06:21:09 +00:00
|
|
|
RakNet::BitStream bsIn(&packet->data[1], packet->length, false);
|
2016-10-26 12:55:34 +00:00
|
|
|
bsIn.Read(guid);
|
2016-01-04 12:17:30 +00:00
|
|
|
|
2016-01-12 03:41:44 +00:00
|
|
|
DedicatedPlayer *pl = 0;
|
2016-10-26 12:55:34 +00:00
|
|
|
static RakNet::RakNetGUID myGuid = getLocalPlayer()->guid;
|
|
|
|
if (guid != myGuid)
|
2016-11-15 19:54:06 +00:00
|
|
|
pl = Players::getPlayer(guid);
|
2016-01-04 12:17:30 +00:00
|
|
|
|
2016-10-19 19:49:35 +00:00
|
|
|
PlayerPacket *myPacket = playerController.GetPacket(packet->data[0]);
|
2016-01-04 12:17:30 +00:00
|
|
|
|
2016-08-17 15:20:36 +00:00
|
|
|
switch (packet->data[0])
|
2016-01-04 12:17:30 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
case ID_HANDSHAKE:
|
|
|
|
{
|
2016-11-15 19:54:06 +00:00
|
|
|
(*getLocalPlayer()->getPassw()) = "SuperPassword";
|
2016-10-21 16:23:56 +00:00
|
|
|
myPacket->Send(getLocalPlayer(), serverAddr);
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_GAME_BASE_INFO:
|
|
|
|
{
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_INFO, "Received ID_GAME_BASE_INFO from server");
|
2016-10-21 16:23:56 +00:00
|
|
|
|
2016-10-26 12:55:34 +00:00
|
|
|
if (guid == myGuid)
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_APPEND(Log::LOG_INFO, "- Packet was about my id");
|
2016-08-17 18:18:04 +00:00
|
|
|
|
2016-10-21 16:23:56 +00:00
|
|
|
if (packet->length == myPacket->headerSize())
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_APPEND(Log::LOG_INFO, "- Requesting info");
|
2016-10-21 16:23:56 +00:00
|
|
|
myPacket->Send(getLocalPlayer(), serverAddr);
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
myPacket->Packet(&bsIn, getLocalPlayer(), false);
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_APPEND(Log::LOG_INFO, "- Updating LocalPlayer");
|
2016-10-21 16:23:56 +00:00
|
|
|
getLocalPlayer()->updateChar();
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
else
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
LOG_APPEND(Log::LOG_INFO, "- Packet was about %s", pl == 0 ? "new player" : pl->Npc()->mName.c_str());
|
|
|
|
|
|
|
|
if (pl == 0)
|
2016-07-17 09:53:55 +00:00
|
|
|
{
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_APPEND(Log::LOG_INFO, "- Exchanging data with new player");
|
2016-11-15 19:54:06 +00:00
|
|
|
pl = Players::newPlayer(guid);
|
2016-07-17 09:53:55 +00:00
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
|
|
|
|
myPacket->Packet(&bsIn, pl, false);
|
2016-11-15 19:54:06 +00:00
|
|
|
Players::createPlayer(guid);
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_GAME_POS:
|
|
|
|
{
|
2016-10-26 12:55:34 +00:00
|
|
|
if (guid == myGuid)
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
if (packet->length != myPacket->headerSize())
|
|
|
|
{
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_INFO, "ID_GAME_POS changed by server");
|
2016-10-21 16:23:56 +00:00
|
|
|
myPacket->Packet(&bsIn, getLocalPlayer(), false);
|
|
|
|
getLocalPlayer()->setPosition();
|
|
|
|
}
|
|
|
|
else
|
|
|
|
getLocalPlayer()->updatePosition(true);
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
else if (pl != 0)
|
2016-10-27 16:09:05 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
myPacket->Packet(&bsIn, pl, false);
|
2016-10-27 16:09:05 +00:00
|
|
|
pl->updateMarker();
|
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_USER_MYID:
|
|
|
|
{
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_INFO, "Received ID_USER_MYID from server");
|
2016-10-26 12:55:34 +00:00
|
|
|
myGuid = guid;
|
|
|
|
getLocalPlayer()->guid = guid;
|
2016-10-21 16:23:56 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_USER_DISCONNECTED:
|
|
|
|
{
|
2016-10-26 12:55:34 +00:00
|
|
|
if (guid == myGuid)
|
2016-10-21 16:23:56 +00:00
|
|
|
MWBase::Environment::get().getStateManager()->requestQuit();
|
|
|
|
else if (pl != 0)
|
2016-11-15 19:54:06 +00:00
|
|
|
Players::disconnectPlayer(guid);
|
2016-01-12 03:41:44 +00:00
|
|
|
|
2016-10-21 16:23:56 +00:00
|
|
|
}
|
|
|
|
case ID_GAME_EQUIPMENT:
|
|
|
|
{
|
2016-10-26 12:55:34 +00:00
|
|
|
if (guid == myGuid)
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
if (packet->length == myPacket->headerSize())
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-11-17 20:33:30 +00:00
|
|
|
getLocalPlayer()->updateEquipment(true);
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
else
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
myPacket->Packet(&bsIn, getLocalPlayer(), false);
|
2016-11-17 20:33:30 +00:00
|
|
|
getLocalPlayer()->setEquipment();
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
else if (pl != 0)
|
|
|
|
{
|
|
|
|
myPacket->Packet(&bsIn, pl, false);
|
2016-11-17 20:33:30 +00:00
|
|
|
pl->updateEquipment();
|
2016-10-21 16:23:56 +00:00
|
|
|
}
|
|
|
|
break;
|
|
|
|
}
|
2016-10-31 15:16:41 +00:00
|
|
|
case ID_GAME_INVENTORY:
|
|
|
|
{
|
|
|
|
if (guid == myGuid)
|
|
|
|
{
|
|
|
|
if (packet->length == myPacket->headerSize())
|
|
|
|
{
|
|
|
|
getLocalPlayer()->updateInventory(true);
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
myPacket->Packet(&bsIn, getLocalPlayer(), false);
|
2016-11-20 02:06:33 +00:00
|
|
|
MWWorld::Ptr ptrPlayer = MWBase::Environment::get().getWorld()->getPlayerPtr();
|
|
|
|
MWWorld::ContainerStore &conStore = ptrPlayer.getClass().getContainerStore(ptrPlayer);
|
|
|
|
|
2016-10-31 15:16:41 +00:00
|
|
|
if (getLocalPlayer()->inventory.action == Inventory::ADDITEM)
|
|
|
|
{
|
|
|
|
for (unsigned int i = 0; i < getLocalPlayer()->inventory.count; i++)
|
|
|
|
{
|
|
|
|
mwmp::Item item = getLocalPlayer()->inventory.items[i];
|
2016-11-20 02:06:33 +00:00
|
|
|
MWWorld::Ptr itemPtr = *conStore.add(item.refid, item.count, ptrPlayer);
|
2016-10-31 15:16:41 +00:00
|
|
|
if (item.health != -1)
|
|
|
|
itemPtr.getCellRef().setCharge(item.health);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else if (getLocalPlayer()->inventory.action == Inventory::REMOVEITEM)
|
|
|
|
{
|
|
|
|
for (unsigned int i = 0; i < getLocalPlayer()->inventory.count; i++)
|
|
|
|
{
|
|
|
|
mwmp::Item item = getLocalPlayer()->inventory.items[i];
|
2016-11-20 02:06:33 +00:00
|
|
|
conStore.remove(item.refid, item.count, ptrPlayer);
|
2016-10-31 15:16:41 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
else // update
|
|
|
|
{
|
2016-11-20 02:06:33 +00:00
|
|
|
// Clear items in inventory
|
2016-10-31 15:16:41 +00:00
|
|
|
conStore.clear();
|
2016-11-20 02:06:33 +00:00
|
|
|
|
2016-10-31 15:16:41 +00:00
|
|
|
for (unsigned int i = 0; i < getLocalPlayer()->inventory.count; i++)
|
|
|
|
{
|
|
|
|
mwmp::Item item = getLocalPlayer()->inventory.items[i];
|
2016-11-20 02:06:33 +00:00
|
|
|
MWWorld::Ptr itemPtr = *conStore.add(item.refid, item.count, ptrPlayer);
|
2016-10-31 15:16:41 +00:00
|
|
|
if (item.health != -1)
|
|
|
|
itemPtr.getCellRef().setCharge(item.health);
|
|
|
|
}
|
2016-11-20 02:06:33 +00:00
|
|
|
|
|
|
|
// Don't automatically setEquipment() here, or the player could end
|
|
|
|
// up getting a new set of their starting clothes, or other items
|
|
|
|
// supposed to no longer exist
|
|
|
|
//
|
|
|
|
// Instead, expect server scripts to do that manually
|
2016-10-31 15:16:41 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
break;
|
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
case ID_GAME_ATTACK:
|
|
|
|
{
|
|
|
|
if (pl != 0)
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
myPacket->Packet(&bsIn, pl, false);
|
|
|
|
|
2016-11-15 19:54:06 +00:00
|
|
|
//cout << "Player: " << pl->Npc()->mName << " pressed: " << (pl->getAttack()->pressed == 1) << endl;
|
|
|
|
if (pl->getAttack()->pressed == 0)
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_VERBOSE, "Attack success: %s",
|
2016-11-15 19:54:06 +00:00
|
|
|
pl->getAttack()->success ? "true" : "false");
|
2016-01-12 03:41:44 +00:00
|
|
|
|
2016-11-15 19:54:06 +00:00
|
|
|
if (pl->getAttack()->success == 1)
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_VERBOSE, "Damage: %f",
|
2016-11-15 19:54:06 +00:00
|
|
|
pl->getAttack()->damage);
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
}
|
2016-01-12 03:41:44 +00:00
|
|
|
|
2016-10-21 16:23:56 +00:00
|
|
|
MWMechanics::CreatureStats &stats = pl->getPtr().getClass().getNpcStats(pl->getPtr());
|
2016-11-15 19:54:06 +00:00
|
|
|
stats.getSpells().setSelectedSpell(pl->getAttack()->refid);
|
2016-01-12 03:41:44 +00:00
|
|
|
|
2016-10-21 16:23:56 +00:00
|
|
|
MWWorld::Ptr victim;
|
2016-11-15 19:54:06 +00:00
|
|
|
if (pl->getAttack()->target == getLocalPlayer()->guid)
|
2016-10-21 16:23:56 +00:00
|
|
|
victim = MWBase::Environment::get().getWorld()->getPlayerPtr();
|
2016-11-15 19:54:06 +00:00
|
|
|
else if (Players::getPlayer(pl->getAttack()->target) != 0)
|
|
|
|
victim = Players::getPlayer(pl->getAttack()->target)->getPtr();
|
2016-01-12 03:41:44 +00:00
|
|
|
|
2016-10-21 16:23:56 +00:00
|
|
|
MWWorld::Ptr attacker;
|
|
|
|
attacker = pl->getPtr();
|
2016-01-12 03:41:44 +00:00
|
|
|
|
2016-10-21 16:23:56 +00:00
|
|
|
// Get the weapon used (if hand-to-hand, weapon = inv.end())
|
|
|
|
if (*pl->DrawState() == 1)
|
|
|
|
{
|
|
|
|
MWWorld::InventoryStore &inv = attacker.getClass().getInventoryStore(attacker);
|
|
|
|
MWWorld::ContainerStoreIterator weaponslot = inv.getSlot(
|
|
|
|
MWWorld::InventoryStore::Slot_CarriedRight);
|
|
|
|
MWWorld::Ptr weapon = ((weaponslot != inv.end()) ? *weaponslot : MWWorld::Ptr());
|
|
|
|
if (!weapon.isEmpty() && weapon.getTypeName() != typeid(ESM::Weapon).name())
|
|
|
|
weapon = MWWorld::Ptr();
|
|
|
|
|
|
|
|
if (victim.mRef != 0)
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
bool healthdmg;
|
|
|
|
if (!weapon.isEmpty())
|
|
|
|
healthdmg = true;
|
|
|
|
else
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
MWMechanics::CreatureStats &otherstats = victim.getClass().getCreatureStats(victim);
|
|
|
|
healthdmg = otherstats.isParalyzed() || otherstats.getKnockedDown();
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
|
|
|
|
if (!weapon.isEmpty())
|
2016-11-15 19:54:06 +00:00
|
|
|
MWMechanics::blockMeleeAttack(attacker, victim, weapon, pl->getAttack()->damage, 1);
|
|
|
|
pl->getPtr().getClass().onHit(victim, pl->getAttack()->damage, healthdmg, weapon, attacker, osg::Vec3f(),
|
|
|
|
pl->getAttack()->success);
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
else
|
|
|
|
{
|
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_VERBOSE, "SpellId: %s",
|
2016-11-15 19:54:06 +00:00
|
|
|
pl->getAttack()->refid.c_str());
|
|
|
|
LOG_APPEND(Log::LOG_VERBOSE, " - success: %d", pl->getAttack()->success);
|
2016-10-21 16:23:56 +00:00
|
|
|
}
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_GAME_DYNAMICSTATS:
|
|
|
|
{
|
2016-10-26 12:55:34 +00:00
|
|
|
if (guid == myGuid)
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
if (packet->length == myPacket->headerSize())
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
getLocalPlayer()->updateDynamicStats(true);
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
else
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
myPacket->Packet(&bsIn, getLocalPlayer(), false);
|
|
|
|
getLocalPlayer()->setDynamicStats();
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
else if (pl != 0)
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
myPacket->Packet(&bsIn, pl, false);
|
|
|
|
|
|
|
|
MWWorld::Ptr ptrPlayer = pl->getPtr();
|
|
|
|
MWMechanics::CreatureStats *ptrCreatureStats = &ptrPlayer.getClass().getCreatureStats(ptrPlayer);
|
|
|
|
MWMechanics::DynamicStat<float> value;
|
|
|
|
|
|
|
|
for (int i = 0; i < 3; ++i)
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
value.readState(pl->CreatureStats()->mDynamic[i]);
|
|
|
|
ptrCreatureStats->setDynamic(i, value);
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_GAME_DIE:
|
|
|
|
{
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_INFO, "Received ID_GAME_DIE from server");
|
2016-10-26 12:55:34 +00:00
|
|
|
if (guid == myGuid)
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
MWWorld::Ptr player = MWBase::Environment::get().getWorld()->getPlayerPtr();
|
|
|
|
MWMechanics::DynamicStat<float> health = player.getClass().getCreatureStats(player).getHealth();
|
|
|
|
health.setCurrent(0);
|
|
|
|
player.getClass().getCreatureStats(player).setHealth(health);
|
|
|
|
myPacket->Send(getLocalPlayer(), serverAddr);
|
|
|
|
}
|
|
|
|
else if (pl != 0)
|
|
|
|
{
|
|
|
|
LOG_APPEND(Log::LOG_INFO, "- Packet was about %s", pl->Npc()->mName.c_str());
|
|
|
|
MWMechanics::DynamicStat<float> health;
|
|
|
|
pl->CreatureStats()->mDead = true;
|
|
|
|
health.readState(pl->CreatureStats()->mDynamic[0]);
|
|
|
|
health.setCurrent(0);
|
|
|
|
health.writeState(pl->CreatureStats()->mDynamic[0]);
|
|
|
|
pl->getPtr().getClass().getCreatureStats(pl->getPtr()).setHealth(health);
|
|
|
|
}
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_GAME_RESURRECT:
|
|
|
|
{
|
2016-10-26 12:55:34 +00:00
|
|
|
if (guid == myGuid)
|
2016-10-21 16:23:56 +00:00
|
|
|
{
|
|
|
|
MWWorld::Ptr player = MWBase::Environment::get().getWorld()->getPlayerPtr();
|
|
|
|
player.getClass().getCreatureStats(player).resurrect();
|
|
|
|
ESM::Position pos;
|
|
|
|
MWBase::Environment::get().getWorld()->findInteriorPosition("Pelagiad, Fort Pelagiad", pos);
|
|
|
|
MWBase::Environment::get().getWorld()->changeToInteriorCell("Pelagiad, Fort Pelagiad", pos, true);
|
|
|
|
(*getLocalPlayer()->Position()) = pos;
|
2016-11-16 15:43:58 +00:00
|
|
|
(*getLocalPlayer()->getCell()) = *player.getCell()->getCell();
|
2016-10-21 16:23:56 +00:00
|
|
|
myPacket->Send(getLocalPlayer(), serverAddr);
|
2016-01-12 03:41:44 +00:00
|
|
|
|
2016-10-21 16:23:56 +00:00
|
|
|
getLocalPlayer()->updateDynamicStats(true);
|
|
|
|
playerController.GetPacket(ID_GAME_DYNAMICSTATS)->Send(getLocalPlayer(), serverAddr);
|
|
|
|
}
|
|
|
|
else if (pl != 0)
|
|
|
|
{
|
|
|
|
pl->CreatureStats()->mDead = false;
|
|
|
|
if (pl->CreatureStats()->mDynamic[0].mMod < 1)
|
|
|
|
pl->CreatureStats()->mDynamic[0].mMod = 1;
|
|
|
|
pl->CreatureStats()->mDynamic[0].mCurrent = pl->CreatureStats()->mDynamic[0].mMod;
|
2016-01-04 12:17:30 +00:00
|
|
|
|
2016-10-21 16:23:56 +00:00
|
|
|
pl->getPtr().getClass().getCreatureStats(pl->getPtr()).resurrect();
|
2016-01-12 03:41:44 +00:00
|
|
|
|
2016-10-21 16:23:56 +00:00
|
|
|
MWMechanics::DynamicStat<float> health;
|
|
|
|
health.readState(pl->CreatureStats()->mDynamic[0]);
|
|
|
|
pl->getPtr().getClass().getCreatureStats(pl->getPtr()).setHealth(health);
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_GAME_CELL:
|
|
|
|
{
|
2016-10-26 12:55:34 +00:00
|
|
|
if (guid == myGuid)
|
2016-09-29 10:17:46 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
if (packet->length == myPacket->headerSize())
|
|
|
|
getLocalPlayer()->updateCell(true);
|
|
|
|
else
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
myPacket->Packet(&bsIn, getLocalPlayer(), false);
|
|
|
|
getLocalPlayer()->setCell();
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
2016-09-29 10:17:46 +00:00
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
else if (pl != 0)
|
2016-09-29 10:17:46 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
myPacket->Packet(&bsIn, pl, false);
|
|
|
|
pl->updateCell();
|
2016-09-29 10:17:46 +00:00
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_GAME_DRAWSTATE:
|
|
|
|
{
|
2016-10-26 12:55:34 +00:00
|
|
|
if (guid == myGuid)
|
2016-10-21 16:23:56 +00:00
|
|
|
getLocalPlayer()->updateDrawStateAndFlags(true);
|
|
|
|
else if (pl != 0)
|
2016-09-29 10:17:46 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
myPacket->Packet(&bsIn, pl, false);
|
2016-11-15 19:54:06 +00:00
|
|
|
pl->updateDrawState();
|
2016-10-21 16:23:56 +00:00
|
|
|
}
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_CHAT_MESSAGE:
|
|
|
|
{
|
|
|
|
std::string message;
|
2016-10-26 12:55:34 +00:00
|
|
|
if (guid == myGuid)
|
2016-10-21 16:23:56 +00:00
|
|
|
{
|
|
|
|
myPacket->Packet(&bsIn, getLocalPlayer(), false);
|
|
|
|
message = *getLocalPlayer()->ChatMessage();
|
|
|
|
}
|
|
|
|
else if (pl != 0)
|
|
|
|
{
|
|
|
|
myPacket->Packet(&bsIn, pl, false);
|
|
|
|
message = *pl->ChatMessage();
|
|
|
|
}
|
2016-11-15 19:54:06 +00:00
|
|
|
Main::get().getGUIController()->printChatMessage(message);
|
2016-01-12 03:41:44 +00:00
|
|
|
|
2016-10-21 16:23:56 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_GAME_CHARGEN:
|
|
|
|
{
|
2016-10-26 12:55:34 +00:00
|
|
|
if (guid == myGuid)
|
2016-10-21 16:23:56 +00:00
|
|
|
{
|
|
|
|
myPacket->Packet(&bsIn, getLocalPlayer(), false);
|
2016-09-29 10:17:46 +00:00
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_GAME_ATTRIBUTE:
|
|
|
|
{
|
2016-10-26 12:55:34 +00:00
|
|
|
if (guid == myGuid)
|
2016-09-29 10:17:46 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
if (packet->length == myPacket->headerSize())
|
|
|
|
{
|
|
|
|
getLocalPlayer()->updateAttributes(true);
|
|
|
|
}
|
|
|
|
else
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-09-29 10:17:46 +00:00
|
|
|
myPacket->Packet(&bsIn, getLocalPlayer(), false);
|
2016-10-21 16:23:56 +00:00
|
|
|
getLocalPlayer()->setAttributes();
|
2016-09-29 10:17:46 +00:00
|
|
|
}
|
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
else if (pl != 0)
|
2016-09-29 10:17:46 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
myPacket->Packet(&bsIn, pl, false);
|
2016-01-12 03:41:44 +00:00
|
|
|
|
2016-10-21 16:23:56 +00:00
|
|
|
MWWorld::Ptr ptrPlayer = pl->getPtr();
|
|
|
|
MWMechanics::CreatureStats *ptrCreatureStats = &ptrPlayer.getClass().getCreatureStats(ptrPlayer);
|
|
|
|
MWMechanics::AttributeValue attributeValue;
|
2016-09-25 11:28:25 +00:00
|
|
|
|
2016-10-21 16:23:56 +00:00
|
|
|
for (int i = 0; i < 8; ++i)
|
|
|
|
{
|
|
|
|
attributeValue.readState(pl->CreatureStats()->mAttributes[i]);
|
|
|
|
ptrCreatureStats->setAttribute(i, attributeValue);
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
2016-09-29 10:17:46 +00:00
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_GAME_SKILL:
|
|
|
|
{
|
2016-10-26 12:55:34 +00:00
|
|
|
if (guid == myGuid)
|
2016-09-29 10:17:46 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
if (packet->length == myPacket->headerSize())
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
getLocalPlayer()->updateSkills(true);
|
2016-09-29 10:17:46 +00:00
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
else
|
2016-09-29 10:17:46 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
myPacket->Packet(&bsIn, getLocalPlayer(), false);
|
|
|
|
getLocalPlayer()->setSkills();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else if (pl != 0)
|
|
|
|
{
|
|
|
|
myPacket->Packet(&bsIn, pl, false);
|
2016-01-12 03:41:44 +00:00
|
|
|
|
2016-10-21 16:23:56 +00:00
|
|
|
MWWorld::Ptr ptrPlayer = pl->getPtr();
|
|
|
|
MWMechanics::NpcStats *ptrNpcStats = &ptrPlayer.getClass().getNpcStats(ptrPlayer);
|
|
|
|
MWMechanics::SkillValue skillValue;
|
2016-09-25 11:28:25 +00:00
|
|
|
|
2016-10-21 16:23:56 +00:00
|
|
|
for (int i = 0; i < 27; ++i)
|
|
|
|
{
|
|
|
|
skillValue.readState(pl->NpcStats()->mSkills[i]);
|
|
|
|
ptrNpcStats->setSkill(i, skillValue);
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
2016-09-29 10:17:46 +00:00
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_GAME_LEVEL:
|
|
|
|
{
|
2016-10-26 12:55:34 +00:00
|
|
|
if (guid == myGuid)
|
2016-09-29 10:17:46 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
if (packet->length == myPacket->headerSize())
|
2016-09-25 11:28:25 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
getLocalPlayer()->updateLevel(true);
|
2016-09-25 11:28:25 +00:00
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
else
|
2016-09-29 10:17:46 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
myPacket->Packet(&bsIn, getLocalPlayer(), false);
|
|
|
|
getLocalPlayer()->setLevel();
|
2016-09-29 10:17:46 +00:00
|
|
|
}
|
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
else if (pl != 0)
|
2016-09-29 10:17:46 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
myPacket->Packet(&bsIn, pl, false);
|
2016-07-23 14:02:06 +00:00
|
|
|
|
2016-10-21 16:23:56 +00:00
|
|
|
MWWorld::Ptr ptrPlayer = pl->getPtr();
|
|
|
|
MWMechanics::CreatureStats *ptrCreatureStats = &ptrPlayer.getClass().getCreatureStats(ptrPlayer);
|
2016-07-23 14:02:06 +00:00
|
|
|
|
2016-10-21 16:23:56 +00:00
|
|
|
ptrCreatureStats->setLevel(pl->CreatureStats()->mLevel);
|
2016-09-29 10:17:46 +00:00
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_GUI_MESSAGEBOX:
|
|
|
|
{
|
2016-10-26 12:55:34 +00:00
|
|
|
if (guid == myGuid)
|
2016-08-30 03:17:06 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
myPacket->Packet(&bsIn, getLocalPlayer(), false);
|
|
|
|
|
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_INFO, "ID_GUI_MESSAGEBOX, Type %d, MSG %s",
|
|
|
|
getLocalPlayer()->guiMessageBox.type,
|
|
|
|
getLocalPlayer()->guiMessageBox.label.c_str());
|
|
|
|
|
|
|
|
if (getLocalPlayer()->guiMessageBox.type == BasePlayer::GUIMessageBox::MessageBox)
|
2016-11-15 19:54:06 +00:00
|
|
|
Main::get().getGUIController()->showMessageBox(getLocalPlayer()->guiMessageBox);
|
2016-10-21 16:23:56 +00:00
|
|
|
else if (getLocalPlayer()->guiMessageBox.type == BasePlayer::GUIMessageBox::CustomMessageBox)
|
2016-11-15 19:54:06 +00:00
|
|
|
Main::get().getGUIController()->showCustomMessageBox(getLocalPlayer()->guiMessageBox);
|
2016-10-21 16:23:56 +00:00
|
|
|
else if (getLocalPlayer()->guiMessageBox.type == BasePlayer::GUIMessageBox::InputDialog)
|
2016-11-15 19:54:06 +00:00
|
|
|
Main::get().getGUIController()->showInputBox(getLocalPlayer()->guiMessageBox);
|
2016-11-03 16:21:41 +00:00
|
|
|
else if (getLocalPlayer()->guiMessageBox.type == BasePlayer::GUIMessageBox::ListBox)
|
2016-11-15 19:54:06 +00:00
|
|
|
Main::get().getGUIController()->showDialogList(getLocalPlayer()->guiMessageBox);
|
2016-08-30 03:17:06 +00:00
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_GAME_CHARCLASS:
|
|
|
|
{
|
2016-10-26 12:55:34 +00:00
|
|
|
if (guid == myGuid)
|
2016-08-30 05:24:31 +00:00
|
|
|
{
|
2016-10-21 16:23:56 +00:00
|
|
|
if (packet->length == myPacket->headerSize())
|
|
|
|
getLocalPlayer()->sendClass();
|
|
|
|
else
|
2016-08-30 05:24:31 +00:00
|
|
|
{
|
|
|
|
myPacket->Packet(&bsIn, getLocalPlayer(), false);
|
2016-10-21 16:23:56 +00:00
|
|
|
getLocalPlayer()->setClass();
|
2016-08-30 05:24:31 +00:00
|
|
|
}
|
|
|
|
}
|
2016-10-31 20:53:32 +00:00
|
|
|
break;
|
2016-10-23 15:32:03 +00:00
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
case ID_GAME_TIME:
|
|
|
|
{
|
2016-10-26 12:55:34 +00:00
|
|
|
if (guid == myGuid)
|
2016-10-21 16:23:56 +00:00
|
|
|
{
|
|
|
|
myPacket->Packet(&bsIn, getLocalPlayer(), false);
|
|
|
|
MWBase::World *world = MWBase::Environment::get().getWorld();
|
|
|
|
if (getLocalPlayer()->hour != -1)
|
|
|
|
world->setHour(getLocalPlayer()->hour);
|
|
|
|
else if (getLocalPlayer()->day != -1)
|
|
|
|
world->setDay(getLocalPlayer()->day);
|
|
|
|
else if (getLocalPlayer()->month != -1)
|
|
|
|
world->setMonth(getLocalPlayer()->month);
|
|
|
|
}
|
2016-10-21 17:44:15 +00:00
|
|
|
break;
|
2016-11-03 18:59:39 +00:00
|
|
|
}
|
|
|
|
case ID_GAME_CONSOLE:
|
|
|
|
{
|
|
|
|
myPacket->Packet(&bsIn, getLocalPlayer(), false);
|
|
|
|
break;
|
2016-10-21 16:23:56 +00:00
|
|
|
}
|
|
|
|
default:
|
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_INFO, "Unhandled PlayerPacket with identifier %i has arrived",
|
|
|
|
packet->data[0]);
|
2016-01-04 12:17:30 +00:00
|
|
|
}
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
2016-01-04 12:17:30 +00:00
|
|
|
|
2016-11-15 19:54:06 +00:00
|
|
|
void Networking::processWorldPacket(RakNet::Packet *packet)
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-10-26 12:55:34 +00:00
|
|
|
RakNet::RakNetGUID guid;
|
2016-10-21 17:44:15 +00:00
|
|
|
RakNet::BitStream bsIn(&packet->data[1], packet->length, false);
|
2016-10-26 12:55:34 +00:00
|
|
|
bsIn.Read(guid);
|
2016-10-21 17:44:15 +00:00
|
|
|
|
|
|
|
DedicatedPlayer *pl = 0;
|
2016-10-26 12:55:34 +00:00
|
|
|
static RakNet::RakNetGUID myGuid = getLocalPlayer()->guid;
|
|
|
|
if (guid != myGuid)
|
2016-11-15 19:54:06 +00:00
|
|
|
pl = Players::getPlayer(guid);
|
2016-10-21 17:44:15 +00:00
|
|
|
|
2016-10-21 16:23:56 +00:00
|
|
|
WorldPacket *myPacket = worldController.GetPacket(packet->data[0]);
|
2016-10-26 12:55:34 +00:00
|
|
|
WorldEvent *event = new WorldEvent(guid);
|
2016-10-23 10:30:32 +00:00
|
|
|
myPacket->Packet(&bsIn, event, false);
|
2016-10-21 16:23:56 +00:00
|
|
|
|
|
|
|
switch (packet->data[0])
|
|
|
|
{
|
2016-10-25 09:15:27 +00:00
|
|
|
case ID_OBJECT_PLACE:
|
2016-10-21 18:57:05 +00:00
|
|
|
{
|
2016-11-15 17:13:36 +00:00
|
|
|
MWWorld::CellStore *ptrCellStore = Main::get().getWorldController()->getCell(event->cell);
|
2016-11-04 13:47:55 +00:00
|
|
|
|
|
|
|
if (!ptrCellStore) return;
|
|
|
|
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Received ID_OBJECT_PLACE");
|
2016-10-28 19:35:01 +00:00
|
|
|
LOG_APPEND(Log::LOG_WARN, "- cellRef: %s, %i\n- cell: %s\n- count: %i",
|
2016-10-25 11:07:00 +00:00
|
|
|
event->cellRef.mRefID.c_str(),
|
|
|
|
event->cellRef.mRefNum.mIndex,
|
2016-10-28 19:35:01 +00:00
|
|
|
event->cell.getDescription().c_str(),
|
|
|
|
event->count);
|
2016-10-22 09:45:19 +00:00
|
|
|
|
2016-10-25 11:07:00 +00:00
|
|
|
MWWorld::ManualRef ref(MWBase::Environment::get().getWorld()->getStore(), event->cellRef.mRefID, 1);
|
2016-10-28 19:35:01 +00:00
|
|
|
MWWorld::Ptr newPtr = ref.getPtr();
|
|
|
|
|
|
|
|
if (event->count > 1)
|
|
|
|
newPtr.getRefData().setCount(event->count);
|
|
|
|
|
2016-10-29 21:21:55 +00:00
|
|
|
newPtr.getCellRef().setGoldValue(event->cellRef.mGoldValue);
|
|
|
|
|
2016-10-29 21:51:23 +00:00
|
|
|
newPtr = MWBase::Environment::get().getWorld()->placeObject(newPtr, ptrCellStore, event->pos);
|
2016-10-29 21:21:55 +00:00
|
|
|
|
|
|
|
// Change RefNum here because the line above unsets it
|
|
|
|
newPtr.getCellRef().setRefNumIndex(event->cellRef.mRefNum.mIndex);
|
|
|
|
|
|
|
|
// If this RefNum is higher than the last we've recorded for this CellStore,
|
|
|
|
// start using it as our new last one
|
|
|
|
if (ptrCellStore->getLastRefNumIndex() < event->cellRef.mRefNum.mIndex)
|
|
|
|
ptrCellStore->setLastRefNumIndex(event->cellRef.mRefNum.mIndex);
|
2016-10-22 09:45:19 +00:00
|
|
|
|
2016-10-21 18:57:05 +00:00
|
|
|
break;
|
|
|
|
}
|
2016-10-25 09:15:27 +00:00
|
|
|
case ID_OBJECT_DELETE:
|
2016-10-21 16:23:56 +00:00
|
|
|
{
|
2016-11-15 17:13:36 +00:00
|
|
|
MWWorld::CellStore *ptrCellStore = Main::get().getWorldController()->getCell(event->cell);
|
2016-11-04 13:47:55 +00:00
|
|
|
|
|
|
|
if (!ptrCellStore) return;
|
|
|
|
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Received ID_OBJECT_DELETE");
|
2016-10-23 16:10:21 +00:00
|
|
|
LOG_APPEND(Log::LOG_WARN, "- cellRef: %s, %i\n- cell: %s",
|
2016-10-22 11:13:16 +00:00
|
|
|
event->cellRef.mRefID.c_str(),
|
2016-10-23 13:33:53 +00:00
|
|
|
event->cellRef.mRefNum.mIndex,
|
2016-10-23 13:55:30 +00:00
|
|
|
event->cell.getDescription().c_str());
|
2016-10-21 17:44:15 +00:00
|
|
|
|
2016-10-28 18:31:41 +00:00
|
|
|
MWWorld::Ptr ptrFound = ptrCellStore->searchExact(event->cellRef.mRefID, event->cellRef.mRefNum.mIndex);
|
2016-10-22 13:47:11 +00:00
|
|
|
|
2016-10-22 15:19:57 +00:00
|
|
|
if (ptrFound)
|
|
|
|
{
|
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Found %s, %i",
|
|
|
|
ptrFound.getCellRef().getRefId().c_str(),
|
|
|
|
ptrFound.getCellRef().getRefNum());
|
2016-10-22 13:47:11 +00:00
|
|
|
|
2016-10-22 15:19:57 +00:00
|
|
|
MWBase::Environment::get().getWorld()->deleteObject(ptrFound);
|
|
|
|
}
|
2016-10-22 09:45:19 +00:00
|
|
|
|
2016-10-21 17:44:15 +00:00
|
|
|
break;
|
2016-10-21 16:23:56 +00:00
|
|
|
}
|
2016-10-25 09:15:27 +00:00
|
|
|
case ID_OBJECT_LOCK:
|
2016-10-24 10:20:04 +00:00
|
|
|
{
|
2016-11-15 17:13:36 +00:00
|
|
|
MWWorld::CellStore *ptrCellStore = Main::get().getWorldController()->getCell(event->cell);
|
2016-11-04 13:47:55 +00:00
|
|
|
|
|
|
|
if (!ptrCellStore) return;
|
|
|
|
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Received ID_OBJECT_LOCK");
|
2016-10-24 10:20:04 +00:00
|
|
|
LOG_APPEND(Log::LOG_WARN, "- cellRef: %s, %i\n- cell: %s",
|
|
|
|
event->cellRef.mRefID.c_str(),
|
|
|
|
event->cellRef.mRefNum.mIndex,
|
|
|
|
event->cell.getDescription().c_str());
|
|
|
|
|
2016-10-28 18:31:41 +00:00
|
|
|
MWWorld::Ptr ptrFound = ptrCellStore->searchExact(event->cellRef.mRefID, event->cellRef.mRefNum.mIndex);
|
2016-10-24 10:20:04 +00:00
|
|
|
|
|
|
|
if (ptrFound)
|
|
|
|
{
|
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Found %s, %i",
|
|
|
|
ptrFound.getCellRef().getRefId().c_str(),
|
|
|
|
ptrFound.getCellRef().getRefNum());
|
|
|
|
|
|
|
|
ptrFound.getClass().lock(ptrFound, event->lockLevel);
|
|
|
|
}
|
|
|
|
|
|
|
|
break;
|
|
|
|
}
|
2016-10-25 09:15:27 +00:00
|
|
|
case ID_OBJECT_UNLOCK:
|
2016-10-24 08:26:31 +00:00
|
|
|
{
|
2016-11-15 17:13:36 +00:00
|
|
|
MWWorld::CellStore *ptrCellStore = Main::get().getWorldController()->getCell(event->cell);
|
2016-11-04 13:47:55 +00:00
|
|
|
|
|
|
|
if (!ptrCellStore) return;
|
|
|
|
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Received ID_OBJECT_UNLOCK");
|
2016-10-24 08:26:31 +00:00
|
|
|
LOG_APPEND(Log::LOG_WARN, "- cellRef: %s, %i\n- cell: %s",
|
|
|
|
event->cellRef.mRefID.c_str(),
|
|
|
|
event->cellRef.mRefNum.mIndex,
|
|
|
|
event->cell.getDescription().c_str());
|
|
|
|
|
2016-10-28 18:31:41 +00:00
|
|
|
MWWorld::Ptr ptrFound = ptrCellStore->searchExact(event->cellRef.mRefID, event->cellRef.mRefNum.mIndex);
|
2016-10-24 08:26:31 +00:00
|
|
|
|
|
|
|
if (ptrFound)
|
|
|
|
{
|
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Found %s, %i",
|
|
|
|
ptrFound.getCellRef().getRefId().c_str(),
|
|
|
|
ptrFound.getCellRef().getRefNum());
|
|
|
|
|
|
|
|
ptrFound.getClass().unlock(ptrFound);
|
|
|
|
}
|
|
|
|
|
|
|
|
break;
|
|
|
|
}
|
2016-10-25 09:15:27 +00:00
|
|
|
case ID_OBJECT_SCALE:
|
2016-10-24 21:52:42 +00:00
|
|
|
{
|
2016-11-15 17:13:36 +00:00
|
|
|
MWWorld::CellStore *ptrCellStore = Main::get().getWorldController()->getCell(event->cell);
|
2016-11-04 13:47:55 +00:00
|
|
|
|
|
|
|
if (!ptrCellStore) return;
|
|
|
|
|
2016-10-25 09:15:27 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "%s", "Received ID_OBJECT_SCALE");
|
2016-10-24 21:52:42 +00:00
|
|
|
LOG_APPEND(Log::LOG_WARN, "- cellRef: %s, %i\n- cell: %s",
|
|
|
|
event->cellRef.mRefID.c_str(),
|
|
|
|
event->cellRef.mRefNum.mIndex,
|
|
|
|
event->cell.getDescription().c_str());
|
|
|
|
|
2016-10-28 18:31:41 +00:00
|
|
|
MWWorld::Ptr ptrFound = ptrCellStore->searchExact(event->cellRef.mRefID, event->cellRef.mRefNum.mIndex);
|
2016-10-24 21:52:42 +00:00
|
|
|
|
|
|
|
if (ptrFound)
|
|
|
|
{
|
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Found %s, %i",
|
|
|
|
ptrFound.getCellRef().getRefId().c_str(),
|
|
|
|
ptrFound.getCellRef().getRefNum());
|
|
|
|
|
|
|
|
MWBase::Environment::get().getWorld()->scaleObject(ptrFound, event->scale);
|
|
|
|
}
|
|
|
|
|
|
|
|
break;
|
|
|
|
}
|
2016-10-25 11:07:00 +00:00
|
|
|
case ID_OBJECT_MOVE:
|
|
|
|
{
|
2016-11-15 17:13:36 +00:00
|
|
|
MWWorld::CellStore *ptrCellStore = Main::get().getWorldController()->getCell(event->cell);
|
2016-11-04 13:47:55 +00:00
|
|
|
|
|
|
|
if (!ptrCellStore) return;
|
|
|
|
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Received ID_OBJECT_MOVE");
|
2016-10-25 11:07:00 +00:00
|
|
|
LOG_APPEND(Log::LOG_WARN, "- cellRef: %s, %i\n- cell: %s",
|
|
|
|
event->cellRef.mRefID.c_str(),
|
|
|
|
event->cellRef.mRefNum.mIndex,
|
|
|
|
event->cell.getDescription().c_str());
|
|
|
|
|
2016-10-28 18:31:41 +00:00
|
|
|
MWWorld::Ptr ptrFound = ptrCellStore->searchExact(event->cellRef.mRefID, event->cellRef.mRefNum.mIndex);
|
2016-10-25 11:07:00 +00:00
|
|
|
|
|
|
|
if (ptrFound)
|
|
|
|
{
|
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Found %s, %i",
|
|
|
|
ptrFound.getCellRef().getRefId().c_str(),
|
|
|
|
ptrFound.getCellRef().getRefNum());
|
|
|
|
|
2016-10-27 13:09:02 +00:00
|
|
|
MWBase::Environment::get().getWorld()->moveObject(ptrFound,
|
|
|
|
event->pos.pos[0], event->pos.pos[1], event->pos.pos[2]);
|
2016-10-25 11:07:00 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
break;
|
|
|
|
}
|
2016-10-25 11:28:39 +00:00
|
|
|
case ID_OBJECT_ROTATE:
|
|
|
|
{
|
2016-11-15 17:13:36 +00:00
|
|
|
MWWorld::CellStore *ptrCellStore = Main::get().getWorldController()->getCell(event->cell);
|
2016-11-04 13:47:55 +00:00
|
|
|
|
|
|
|
if (!ptrCellStore) return;
|
|
|
|
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Received ID_OBJECT_ROTATE");
|
2016-10-25 11:28:39 +00:00
|
|
|
LOG_APPEND(Log::LOG_WARN, "- cellRef: %s, %i\n- cell: %s",
|
|
|
|
event->cellRef.mRefID.c_str(),
|
|
|
|
event->cellRef.mRefNum.mIndex,
|
|
|
|
event->cell.getDescription().c_str());
|
|
|
|
|
2016-10-28 18:31:41 +00:00
|
|
|
MWWorld::Ptr ptrFound = ptrCellStore->searchExact(event->cellRef.mRefID, event->cellRef.mRefNum.mIndex);
|
2016-10-25 11:28:39 +00:00
|
|
|
|
|
|
|
if (ptrFound)
|
|
|
|
{
|
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Found %s, %i",
|
|
|
|
ptrFound.getCellRef().getRefId().c_str(),
|
|
|
|
ptrFound.getCellRef().getRefNum());
|
|
|
|
|
2016-10-27 13:09:02 +00:00
|
|
|
MWBase::Environment::get().getWorld()->rotateObject(ptrFound,
|
|
|
|
event->pos.rot[0], event->pos.rot[1], event->pos.rot[2]);
|
|
|
|
}
|
|
|
|
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_OBJECT_ANIM_PLAY:
|
|
|
|
{
|
2016-11-15 17:13:36 +00:00
|
|
|
MWWorld::CellStore *ptrCellStore = Main::get().getWorldController()->getCell(event->cell);
|
2016-11-04 13:47:55 +00:00
|
|
|
|
|
|
|
if (!ptrCellStore) return;
|
|
|
|
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Received ID_OBJECT_ANIM_PLAY");
|
2016-10-27 13:09:02 +00:00
|
|
|
LOG_APPEND(Log::LOG_WARN, "- cellRef: %s, %i\n- cell: %s",
|
|
|
|
event->cellRef.mRefID.c_str(),
|
|
|
|
event->cellRef.mRefNum.mIndex,
|
|
|
|
event->cell.getDescription().c_str());
|
|
|
|
|
2016-10-28 18:31:41 +00:00
|
|
|
MWWorld::Ptr ptrFound = ptrCellStore->searchExact(event->cellRef.mRefID, event->cellRef.mRefNum.mIndex);
|
2016-10-27 13:09:02 +00:00
|
|
|
|
|
|
|
if (ptrFound)
|
|
|
|
{
|
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Found %s, %i",
|
|
|
|
ptrFound.getCellRef().getRefId().c_str(),
|
|
|
|
ptrFound.getCellRef().getRefNum());
|
|
|
|
|
|
|
|
MWBase::Environment::get().getMechanicsManager()->playAnimationGroup(ptrFound,
|
|
|
|
event->animGroup, event->animMode, std::numeric_limits<int>::max(), true);
|
2016-10-25 11:28:39 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
break;
|
|
|
|
}
|
2016-10-25 09:15:27 +00:00
|
|
|
case ID_DOOR_ACTIVATE:
|
2016-10-25 07:40:55 +00:00
|
|
|
{
|
2016-11-15 17:13:36 +00:00
|
|
|
MWWorld::CellStore *ptrCellStore = Main::get().getWorldController()->getCell(event->cell);
|
2016-11-04 13:47:55 +00:00
|
|
|
|
|
|
|
if (!ptrCellStore) return;
|
|
|
|
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Received ID_DOOR_ACTIVATE");
|
2016-10-25 07:40:55 +00:00
|
|
|
LOG_APPEND(Log::LOG_WARN, "- cellRef: %s, %i\n- cell: %s",
|
|
|
|
event->cellRef.mRefID.c_str(),
|
|
|
|
event->cellRef.mRefNum.mIndex,
|
|
|
|
event->cell.getDescription().c_str());
|
|
|
|
|
2016-10-28 18:31:41 +00:00
|
|
|
MWWorld::Ptr ptrFound = ptrCellStore->searchExact(event->cellRef.mRefID, event->cellRef.mRefNum.mIndex);
|
2016-10-25 07:40:55 +00:00
|
|
|
|
|
|
|
if (ptrFound)
|
|
|
|
{
|
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Found %s, %i",
|
|
|
|
ptrFound.getCellRef().getRefId().c_str(),
|
|
|
|
ptrFound.getCellRef().getRefNum());
|
|
|
|
|
|
|
|
ptrFound.getClass().setDoorState(ptrFound, event->state);
|
|
|
|
MWBase::Environment::get().getWorld()->saveDoorState(ptrFound, event->state);
|
|
|
|
}
|
|
|
|
|
|
|
|
break;
|
|
|
|
}
|
2016-10-25 09:15:27 +00:00
|
|
|
case ID_VIDEO_PLAY:
|
2016-10-24 14:52:19 +00:00
|
|
|
{
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Received ID_VIDEO_PLAY");
|
2016-10-24 14:52:19 +00:00
|
|
|
LOG_APPEND(Log::LOG_WARN, "- video: %s\n- allowSkipping: %s",
|
|
|
|
event->video.c_str(),
|
|
|
|
event->allowSkipping ? "true" : "false");
|
|
|
|
|
|
|
|
MWBase::Environment::get().getWindowManager()->playVideo(event->video, event->allowSkipping);
|
|
|
|
|
|
|
|
break;
|
|
|
|
}
|
2016-10-26 09:25:50 +00:00
|
|
|
case ID_SCRIPT_LOCAL_SHORT:
|
|
|
|
{
|
2016-11-15 17:13:36 +00:00
|
|
|
MWWorld::CellStore *ptrCellStore = Main::get().getWorldController()->getCell(event->cell);
|
2016-11-04 13:47:55 +00:00
|
|
|
|
|
|
|
if (!ptrCellStore) return;
|
|
|
|
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Received ID_SCRIPT_LOCAL_SHORT");
|
2016-10-26 09:25:50 +00:00
|
|
|
LOG_APPEND(Log::LOG_WARN, "- cellRef: %s, %i\n- cell: %s\n- index: %i\n- shortVal: %i",
|
|
|
|
event->cellRef.mRefID.c_str(),
|
|
|
|
event->cellRef.mRefNum.mIndex,
|
|
|
|
event->cell.getDescription().c_str(),
|
|
|
|
event->index,
|
|
|
|
event->shortVal);
|
|
|
|
|
2016-10-28 18:31:41 +00:00
|
|
|
MWWorld::Ptr ptrFound = ptrCellStore->searchExact(event->cellRef.mRefID, event->cellRef.mRefNum.mIndex);
|
2016-10-26 09:25:50 +00:00
|
|
|
|
|
|
|
if (ptrFound)
|
|
|
|
{
|
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Found %s, %i",
|
|
|
|
ptrFound.getCellRef().getRefId().c_str(),
|
|
|
|
ptrFound.getCellRef().getRefNum());
|
|
|
|
|
|
|
|
ptrFound.getRefData().getLocals().mShorts.at(event->index) = event->shortVal;
|
|
|
|
}
|
|
|
|
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
case ID_SCRIPT_LOCAL_FLOAT:
|
|
|
|
{
|
2016-11-15 17:13:36 +00:00
|
|
|
MWWorld::CellStore *ptrCellStore = Main::get().getWorldController()->getCell(event->cell);
|
2016-11-04 13:47:55 +00:00
|
|
|
|
|
|
|
if (!ptrCellStore) return;
|
|
|
|
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Received ID_SCRIPT_LOCAL_FLOAT");
|
2016-10-26 09:25:50 +00:00
|
|
|
LOG_APPEND(Log::LOG_WARN, "- cellRef: %s, %i\n- cell: %s\n- index: %i\n- floatVal: %f",
|
|
|
|
event->cellRef.mRefID.c_str(),
|
|
|
|
event->cellRef.mRefNum.mIndex,
|
|
|
|
event->cell.getDescription().c_str(),
|
|
|
|
event->index,
|
|
|
|
event->floatVal);
|
|
|
|
|
2016-10-28 18:31:41 +00:00
|
|
|
MWWorld::Ptr ptrFound = ptrCellStore->searchExact(event->cellRef.mRefID, event->cellRef.mRefNum.mIndex);
|
2016-10-26 09:25:50 +00:00
|
|
|
|
|
|
|
if (ptrFound)
|
|
|
|
{
|
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Found %s, %i",
|
|
|
|
ptrFound.getCellRef().getRefId().c_str(),
|
|
|
|
ptrFound.getCellRef().getRefNum());
|
|
|
|
|
|
|
|
ptrFound.getRefData().getLocals().mFloats.at(event->index) = event->floatVal;
|
|
|
|
}
|
|
|
|
|
|
|
|
break;
|
|
|
|
}
|
2016-10-26 21:41:14 +00:00
|
|
|
case ID_SCRIPT_MEMBER_SHORT:
|
|
|
|
{
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Received ID_SCRIPT_MEMBER_SHORT");
|
2016-10-26 21:41:14 +00:00
|
|
|
LOG_APPEND(Log::LOG_WARN, "- cellRef: %s\n- index: %i\n- shortVal: %i\n",
|
|
|
|
event->cellRef.mRefID.c_str(),
|
|
|
|
event->index,
|
|
|
|
event->shortVal);
|
|
|
|
|
|
|
|
// Mimic the way a Ptr is fetched in InterpreterContext for similar situations
|
|
|
|
MWWorld::Ptr ptrFound = MWBase::Environment::get().getWorld()->getPtr(event->cellRef.mRefID, false);
|
|
|
|
|
|
|
|
if (ptrFound)
|
|
|
|
{
|
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Found %s, %i",
|
|
|
|
ptrFound.getCellRef().getRefId().c_str(),
|
|
|
|
ptrFound.getCellRef().getRefNum());
|
|
|
|
|
|
|
|
std::string scriptId = ptrFound.getClass().getScript(ptrFound);
|
|
|
|
|
|
|
|
ptrFound.getRefData().setLocals(
|
|
|
|
*MWBase::Environment::get().getWorld()->getStore().get<ESM::Script>().find(scriptId));
|
|
|
|
|
2016-10-26 23:18:27 +00:00
|
|
|
ptrFound.getRefData().getLocals().mShorts.at(event->index) = event->shortVal;;
|
2016-10-26 21:41:14 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
break;
|
|
|
|
}
|
2016-10-26 09:25:50 +00:00
|
|
|
case ID_SCRIPT_GLOBAL_SHORT:
|
|
|
|
{
|
2016-11-17 04:39:35 +00:00
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_WARN, "Received ID_SCRIPT_GLOBAL_SHORT");
|
2016-10-26 21:41:14 +00:00
|
|
|
LOG_APPEND(Log::LOG_WARN, "- varName: %s\n- shortVal: %i",
|
|
|
|
event->varName.c_str(),
|
2016-10-26 09:25:50 +00:00
|
|
|
event->shortVal);
|
|
|
|
|
2016-10-26 21:41:14 +00:00
|
|
|
MWBase::Environment::get().getWorld()->setGlobalInt(event->varName, event->shortVal);
|
2016-10-26 09:25:50 +00:00
|
|
|
|
|
|
|
break;
|
|
|
|
}
|
2016-10-21 16:23:56 +00:00
|
|
|
default:
|
|
|
|
LOG_MESSAGE_SIMPLE(Log::LOG_INFO, "Unhandled WorldPacket with identifier %i has arrived",
|
|
|
|
packet->data[0]);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2016-11-15 19:54:06 +00:00
|
|
|
void Networking::receiveMessage(RakNet::Packet *packet)
|
2016-10-21 16:23:56 +00:00
|
|
|
{
|
|
|
|
if (packet->length < 2)
|
|
|
|
return;
|
|
|
|
|
|
|
|
if (playerController.ContainsPacket(packet->data[0]))
|
|
|
|
{
|
2016-11-15 19:54:06 +00:00
|
|
|
processPlayerPacket(packet);
|
2016-10-21 16:23:56 +00:00
|
|
|
}
|
|
|
|
else if (worldController.ContainsPacket(packet->data[0]))
|
|
|
|
{
|
2016-11-15 19:54:06 +00:00
|
|
|
processWorldPacket(packet);
|
2016-01-04 12:17:30 +00:00
|
|
|
}
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
2016-01-04 12:17:30 +00:00
|
|
|
|
2016-11-15 19:54:06 +00:00
|
|
|
PlayerPacket *Networking::getPlayerPacket(RakNet::MessageID id)
|
2016-10-19 19:49:35 +00:00
|
|
|
{
|
|
|
|
return playerController.GetPacket(id);
|
|
|
|
}
|
|
|
|
|
2016-11-15 19:54:06 +00:00
|
|
|
WorldPacket *Networking::getWorldPacket(RakNet::MessageID id)
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-10-19 19:49:35 +00:00
|
|
|
return worldController.GetPacket(id);
|
2016-01-04 12:17:30 +00:00
|
|
|
}
|
|
|
|
|
2016-01-12 03:41:44 +00:00
|
|
|
LocalPlayer *Networking::getLocalPlayer()
|
2016-01-04 12:17:30 +00:00
|
|
|
{
|
2016-01-12 03:41:44 +00:00
|
|
|
return mwmp::Main::get().getLocalPlayer();
|
|
|
|
}
|
|
|
|
|
2016-10-20 11:28:19 +00:00
|
|
|
WorldEvent *Networking::createWorldEvent()
|
|
|
|
{
|
|
|
|
return new WorldEvent(getLocalPlayer()->guid);
|
|
|
|
}
|
|
|
|
|
2016-01-12 03:41:44 +00:00
|
|
|
bool Networking::isDedicatedPlayer(const MWWorld::Ptr &ptr)
|
|
|
|
{
|
2016-08-17 15:20:36 +00:00
|
|
|
if (ptr.mRef == 0)
|
2016-01-12 03:41:44 +00:00
|
|
|
return 0;
|
2016-11-15 19:54:06 +00:00
|
|
|
DedicatedPlayer *pl = Players::getPlayer(ptr);
|
2016-01-12 03:41:44 +00:00
|
|
|
|
|
|
|
return pl != 0;
|
|
|
|
}
|
2016-01-04 12:17:30 +00:00
|
|
|
|
2016-11-15 19:54:06 +00:00
|
|
|
bool Networking::attack(const MWWorld::Ptr &ptr)
|
2016-01-12 03:41:44 +00:00
|
|
|
{
|
2016-11-15 19:54:06 +00:00
|
|
|
DedicatedPlayer *pl = Players::getPlayer(ptr);
|
2016-01-12 03:41:44 +00:00
|
|
|
|
2016-08-17 15:20:36 +00:00
|
|
|
if (pl == 0)
|
2016-01-12 03:41:44 +00:00
|
|
|
return false;
|
|
|
|
|
2016-11-15 19:54:06 +00:00
|
|
|
return pl->getAttack()->pressed;
|
2016-01-12 03:41:44 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
bool Networking::isConnected()
|
|
|
|
{
|
|
|
|
return connected;
|
2016-01-04 12:17:30 +00:00
|
|
|
}
|