diff --git a/apps/opencs/model/world/refcollection.cpp b/apps/opencs/model/world/refcollection.cpp index 39f85da70..bd4e69d6b 100644 --- a/apps/opencs/model/world/refcollection.cpp +++ b/apps/opencs/model/world/refcollection.cpp @@ -2,8 +2,10 @@ #include "refcollection.hpp" #include +#include // FIXME: debug only #include +#include #include "ref.hpp" #include "cell.hpp" @@ -20,20 +22,35 @@ void CSMWorld::RefCollection::load (ESM::ESMReader& reader, int cellIndex, bool CellRef ref; bool deleted = false; + ESM::MovedCellRef mref; - while (ESM::Cell::getNextRef (reader, ref, deleted, true)) + // hack to initialise mindex + while (!(mref.mRefNum.mIndex = 0) && ESM::Cell::getNextRef (reader, ref, deleted, true, &mref)) { // Keep mOriginalCell empty when in modified (as an indicator that the // original cell will always be equal the current cell). ref.mOriginalCell = base ? cell2.mId : ""; + if (mref.mRefNum.mIndex != 0 && + ((int)std::floor(ref.mPos.pos[0]/8192) != mref.mTarget[0] || + (int)std::floor(ref.mPos.pos[1]/8192) != mref.mTarget[1])) + { + //std::cout <<"refcollection #" << mref.mTarget[0] << " " << mref.mTarget[1] << std::endl; + } + if (cell.get().isExterior()) { // ignoring moved references sub-record; instead calculate cell from coordinates std::pair index = ref.getCellIndex(); std::ostringstream stream; - stream << "#" << index.first << " " << index.second; + if (mref.mRefNum.mIndex) + { + stream << "#" << mref.mTarget[0] << " " << mref.mTarget[1]; + //std::cout <<"refcollection " + stream.str() << std::endl; + } + else + stream << "#" << index.first << " " << index.second; ref.mCell = stream.str(); } diff --git a/components/esm/loadcell.cpp b/components/esm/loadcell.cpp index d836ec9cf..aed56f415 100644 --- a/components/esm/loadcell.cpp +++ b/components/esm/loadcell.cpp @@ -3,6 +3,7 @@ #include #include #include +#include // FIXME: debugging only #include @@ -168,11 +169,12 @@ std::string Cell::getDescription() const } } -bool Cell::getNextRef(ESMReader &esm, CellRef &ref, bool& deleted, bool ignoreMoves) +bool Cell::getNextRef(ESMReader &esm, CellRef &ref, bool& deleted, bool ignoreMoves, MovedCellRef *mref) { // TODO: Try and document reference numbering, I don't think this has been done anywhere else. if (!esm.hasMoreSubs()) return false; + //bool print = false; // FIXME: debugging only // NOTE: We should not need this check. It is a safety check until we have checked // more plugins, and how they treat these moved references. @@ -180,9 +182,12 @@ bool Cell::getNextRef(ESMReader &esm, CellRef &ref, bool& deleted, bool ignoreMo { if (ignoreMoves) { - MovedCellRef mref; - esm.getHT (mref.mRefNum.mIndex); - esm.getHNOT (mref.mTarget, "CNDT"); + esm.getHT (mref->mRefNum.mIndex); + esm.getHNOT (mref->mTarget, "CNDT"); + //std::cout << "index " + std::to_string(mref->mRefNum.mIndex) + " target " << + //std::to_string(mref->mTarget[0]) + ", " + std::to_string(mref->mTarget[1]) << std::endl; + //print = true; // FIXME: debugging only + adjustRefNum (mref->mRefNum, esm); } else { @@ -194,6 +199,19 @@ bool Cell::getNextRef(ESMReader &esm, CellRef &ref, bool& deleted, bool ignoreMo ref.load (esm); +#if 0 + // FIXME: debugging only + if (print && + ((int)std::floor(ref.mPos.pos[0]/8192) != mref->mTarget[0] || + (int)std::floor(ref.mPos.pos[1]/8192) != mref->mTarget[1])) + { + std::cout << ref.mRefID << + ", " + std::to_string((int)std::floor(ref.mPos.pos[0]/8192)) << + ", " + std::to_string((int)std::floor(ref.mPos.pos[1]/8192)) << + ", Z: " +std::to_string(ref.mPos.pos[2]) << std::endl; + } +#endif + // Identify references belonging to a parent file and adapt the ID accordingly. adjustRefNum (ref.mRefNum, esm); diff --git a/components/esm/loadcell.hpp b/components/esm/loadcell.hpp index 554fa3967..b78d4075a 100644 --- a/components/esm/loadcell.hpp +++ b/components/esm/loadcell.hpp @@ -157,7 +157,8 @@ struct Cell reuse one memory location without blanking it between calls. */ /// \param ignoreMoves ignore MVRF record and read reference like a regular CellRef. - static bool getNextRef(ESMReader &esm, CellRef &ref, bool& deleted, bool ignoreMoves = false); + static bool getNextRef(ESMReader &esm, + CellRef &ref, bool& deleted, bool ignoreMoves = false, MovedCellRef *mref = 0); /* This fetches an MVRF record, which is used to track moved references. * Since they are comparably rare, we use a separate method for this.