void CBMPFormat::unserializeVersion4(void) { CDataReader *pDataReader = CDataReader::getInstance(); uint32 uiByteCount; // read headers 1 & 2 CBMPFormat_Header1 *pHeader1 = pDataReader->readStruct<CBMPFormat_Header1>(); CBMPFormat_Header2_Version4 *pHeader2 = pDataReader->readStruct<CBMPFormat_Header2_Version4>(); // palette m_bHasPalette = pHeader2->m_usBPP < 16; if (m_bHasPalette) { uiByteCount = 4 * pHeader2->m_uiColoursUsed; m_strPaletteData = pDataReader->readString(uiByteCount); } // raster data uiByteCount = pHeader2->m_uiWidth * pHeader2->m_uiHeight * ((float32)pHeader2->m_usBPP / 8.0f); m_strRasterData = pDataReader->readString(uiByteCount); // copy from raw structs to wrapper structs m_uiWidth = pHeader2->m_uiWidth; m_uiHeight = pHeader2->m_uiHeight; m_usColourPlaneCount = pHeader2->m_usPlaneCount; m_usBPP = pHeader2->m_usBPP; // clean up delete pHeader1; delete pHeader2; }
void CRWEntry_2dEffect_Light::unserialize(void) { CDataReader *pDataReader = CDataReader::getInstance(); m_uiColor = pDataReader->readUint32(); m_fCoronaFarClip = pDataReader->readFloat32(); m_fPointlightRange = pDataReader->readFloat32(); m_fCoronaSize = pDataReader->readFloat32(); m_fShadowSize = pDataReader->readFloat32(); m_ucCoronaShowMode = pDataReader->readUint8(); m_ucCoronaEnableReflection = pDataReader->readUint8(); m_ucCoronaFlareType = pDataReader->readUint8(); m_ucShadowColorMultiplier = pDataReader->readUint8(); m_ucFlags1 = pDataReader->readUint8(); m_strCoronaTexName = CStringUtility::rtrimFromLeft(pDataReader->readString(24)); m_strShadowTexName = CStringUtility::rtrimFromLeft(pDataReader->readString(24)); m_ucShadowZDistance = pDataReader->readUint8(); m_ucFlags2 = pDataReader->readUint8(); if (m_uiDataSize == 76) { m_vecPadding.m_x = pDataReader->readUint8(); m_vecPadding.m_y = 0; } else if (m_uiDataSize == 80) { m_vecLookDirection.m_x = pDataReader->readUint8(); m_vecLookDirection.m_y = pDataReader->readUint8(); m_vecLookDirection.m_z = pDataReader->readUint8(); m_vecPadding.m_x = pDataReader->readUint8(); m_vecPadding.m_y = pDataReader->readUint8(); } }
uint8 CBMPFormat::detectBMPVersion(void) { CDataReader *pDataReader = CDataReader::getInstance(); uint8 uiBMPVersion = 0; pDataReader->setPeek(true); string strHeader = pDataReader->readString(2); if (strHeader.c_str()[0] == '\0' && strHeader.c_str()[1] == '\0') { // BMP version 1.x uiBMPVersion = 1; } else if (strHeader.c_str()[0] == 'B' && strHeader.c_str()[1] == 'M') { // BMP version 2.x, 3.x or 4.x pDataReader->setSeek(12); switch (pDataReader->readUint32()) { case 12: // BMP version 2.x uiBMPVersion = 2; break; case 40: // BMP version 3.x uiBMPVersion = 3; break; case 108: // BMP version 4.x uiBMPVersion = 4; } } pDataReader->setPeek(false); pDataReader->setSeek(0); return uiBMPVersion; }
uint32 CCOLEntry::calculateShadowMeshVertexCount(void) { CDataReader *pDataReader = CDataReader::getInstance(); eCOLVersion eCOLVersionValue = getCOLVersion() == nullptr ? COL_UNKNOWN : getCOLVersion()->getVersionId(); //CDebugger::log("getHeaderStartOffset(): " + CStringUtility::toString(getHeaderStartOffset())); //CDebugger::log("getShadowMeshFacesOffset(): " + CStringUtility::toString(getShadowMeshFacesOffset())); //CDebugger::log("getShadowMeshFaceCount(): " + CStringUtility::toString(getShadowMeshFaceCount())); //CDebugger::log("getCOLVersion(): " + CStringUtility::toString(getCOLVersion())); pDataReader->setSeek(getHeaderStartOffset() + 4 + getShadowMeshFacesOffset()); string strShadowMeshFacesData = pDataReader->readString(getShadowMeshFaceCount() * (eCOLVersionValue == 1 ? 16 : 8)); // 12 or 6 = sizeof(TVertex) //CDebugger::log("part 2 -- strShadowMeshFacesData.length(): " + CStringUtility::toString(strShadowMeshFacesData.length())); uint32 uiSeek = 0; uint32 uiHighestVertexIndex = 0; if (getShadowMeshFaceCount() == 0) { return 0; } if (eCOLVersionValue == COL_1) { // COL 1 for (uint32 i = 0, j = getShadowMeshFaceCount(); i < j; i++) { for (uint8 i2 = 0; i2 < 3; i2++) { uint32 uiVertexIndex = CStringUtility::unpackUint32(strShadowMeshFacesData.substr(uiSeek, 4), false); if (uiVertexIndex > uiHighestVertexIndex) { uiHighestVertexIndex = uiVertexIndex; } uiSeek += 4; // 4 is sizeof(uint32) } uiSeek += 4; // 4 is sizeof(TSurface) } } else { // COL 2, 3 & 4 for (uint32 i = 0, j = getShadowMeshFaceCount(); i < j; i++) { for (uint8 i2 = 0; i2 < 3; i2++) { uint32 uiVertexIndex = CStringUtility::unpackUint16(strShadowMeshFacesData.substr(uiSeek, 2), false); if (uiVertexIndex > uiHighestVertexIndex) { uiHighestVertexIndex = uiVertexIndex; } uiSeek += 2; // 2 is sizeof(uint16) } uiSeek += 2; // 1 byte for material, 1 byte for light } } return uiHighestVertexIndex + 1; }
eDATPathFormat CDATPathFormat::detectPathsFormat(void) { CDataReader *pDataReader = CDataReader::getInstance(); eDATPathFormat eDATPathFormatValue; uint32 uiPreviousSeek = pDataReader->getSeek(); pDataReader->setPeek(true); if (CStringUtility::unpackUint32(pDataReader->readString(4), false) == 0xFFFFFFFF && pDataReader->readString(4) == "FM92") { eDATPathFormatValue = DAT_PATH_FASTMAN92; } else { eDATPathFormatValue = DAT_PATH_DEFAULT; } pDataReader->setSeek(uiPreviousSeek); pDataReader->setPeek(false); return eDATPathFormatValue; }
void CDDSFormat::unserialize(void) { CDataReader *pDataReader = CDataReader::getInstance(); // file header uint32 uiMagicNumber = pDataReader->readUint32(); // 0x20534444 // DDS_HEADER structure CDDSFormat_Header_DDS_HEADER *pHeader1 = pDataReader->readStruct<CDDSFormat_Header_DDS_HEADER>(); // DDS_PIXELFORMAT structure CDDSFormat_Header_DDS_PIXELFORMAT_Part1 *pHeader2 = pDataReader->readStruct<CDDSFormat_Header_DDS_PIXELFORMAT_Part1>(); if (pHeader2->m_uiFlags2 == 4/*DDPF_FOURCC*/ && string((char*)&pHeader2->m_ucFourCC, 4) == "DX10") { // DDS_HEADER_DXT10 structure CDDSFormat_Header_DDS_HEADER_DXT10 *pHeader3 = pDataReader->readStruct<CDDSFormat_Header_DDS_HEADER_DXT10>(); delete pHeader3; } // DDS_HEADER structure continued CDDSFormat_Header_DDS_PIXELFORMAT_Part2 *pHeader4 = pDataReader->readStruct<CDDSFormat_Header_DDS_PIXELFORMAT_Part2>(); // raster data m_strRasterData = pDataReader->readString(pHeader1->m_uiWidth * pHeader1->m_uiHeight * (pHeader2->m_uiRGBBitCount / 8)); // copy from raw structs to wrapper structs m_uiWidth = pHeader1->m_uiWidth; m_uiHeight = pHeader1->m_uiHeight; m_uiBPP = pHeader2->m_uiRGBBitCount / 8; // clean up delete pHeader1; delete pHeader2; delete pHeader4; }
void CDATPathFormat::unserializeFastman92(void) { CDataReader *pDataReader = CDataReader::getInstance(); m_uiFileIndex = 0; // uiAreaId; //uint32 uiSeek = 0; //uint32 uiSize; m_header.m_ePathsFormat = DAT_PATH_FASTMAN92; uint32 uiFourCC = pDataReader->readUint32(); // 0xFFFFFFFF string strFormat = pDataReader->readString(4); // FM92 uint8 ucNicknameLength = pDataReader->readUint8(); string strNickname = pDataReader->readString(ucNicknameLength); uint32 uiFormatVersion = pDataReader->readUint32(); m_header.m_uiPathNodeCount = pDataReader->readUint32(); m_header.m_uiVehicleNodeCount = pDataReader->readUint32(); m_header.m_uiPedNodeCount = pDataReader->readUint32(); m_header.m_uiNaviNodeCount = pDataReader->readUint32(); m_header.m_uiLinkCount = pDataReader->readUint32(); //uiSize = pDataReader->getByteCountRead(); //uiSeek += uiSize; m_vecPathNodes.resize(m_header.m_uiPathNodeCount); m_vecNaviNodes.resize(m_header.m_uiNaviNodeCount); m_vecLinks.resize(m_header.m_uiLinkCount); CDATEntry_Paths_Fastman92_PathNode_extended *pPathNodes = new CDATEntry_Paths_Fastman92_PathNode_extended[m_header.m_uiPathNodeCount]; CDATEntry_Paths_Fastman92_NaviNode_extended *pNaviNodes = new CDATEntry_Paths_Fastman92_NaviNode_extended[m_header.m_uiNaviNodeCount]; CDATEntry_Paths_Fastman92_Link *pLinks = new CDATEntry_Paths_Fastman92_Link[m_header.m_uiLinkCount]; CDATEntry_Paths_Fastman92_NaviLink *pNaviLinks = new CDATEntry_Paths_Fastman92_NaviLink[m_header.m_uiLinkCount]; CDATEntry_Paths_Fastman92_LinkLength *pLinkLengths = new CDATEntry_Paths_Fastman92_LinkLength[m_header.m_uiLinkCount]; CDATEntry_Paths_Fastman92_PathIntersectionFlags *pPathIntersectionFlags = new CDATEntry_Paths_Fastman92_PathIntersectionFlags[m_header.m_uiLinkCount]; /* uiSize = pDATFile_Paths->m_header.m_uiPathNodeCount * 40; memcpy(pPathNodes, strFileData.c_str() + uiSeek, uiSize); uiSeek += uiSize; uiSize = pDATFile_Paths->m_header.m_uiNaviNodeCount * 22; memcpy(pNaviNodes, strFileData.c_str() + uiSeek, uiSize); uiSeek += uiSize; uiSize = pDATFile_Paths->m_header.m_uiLinkCount * 4; memcpy(pLinks, strFileData.c_str() + uiSeek, uiSize); uiSeek += uiSize; uiSeek += 768; uiSize = pDATFile_Paths->m_header.m_uiLinkCount * 4; memcpy(pNaviLinks, strFileData.c_str() + uiSeek, uiSize); uiSeek += uiSize; uiSize = pDATFile_Paths->m_header.m_uiLinkCount * 1; memcpy(pLinkLengths, strFileData.c_str() + uiSeek, uiSize); uiSeek += uiSize; */ for (uint32 i = 0, j = m_header.m_uiPathNodeCount; i < j; i++) { CDATEntry_Paths_Fastman92_PathNode_extended *pPathNode_Fastman92 = pPathNodes + i; pPathNode_Fastman92->m_pPrev = 0; pDataReader->readUint32(); pPathNode_Fastman92->m_ppNext = 0; pDataReader->readUint32(); pPathNode_Fastman92->m_posn.x = pDataReader->readUint16(); pPathNode_Fastman92->m_posn.y = pDataReader->readUint16(); pPathNode_Fastman92->m_posn.z = pDataReader->readUint16(); pPathNode_Fastman92->m_wSearchList = pDataReader->readUint16(); pPathNode_Fastman92->m_wConnectedNodesStartId = pDataReader->readUint16(); pPathNode_Fastman92->m_wAreaId = pDataReader->readUint16(); pPathNode_Fastman92->m_wNodeId = pDataReader->readUint16(); pPathNode_Fastman92->m_nPathWidth = pDataReader->readUint8(); pPathNode_Fastman92->m_nNodeType = pDataReader->readUint8(); pPathNode_Fastman92->m_dwFlags = pDataReader->readUint32(); pPathNode_Fastman92->m_extended_posn.x = pDataReader->readUint32(); pPathNode_Fastman92->m_extended_posn.y = pDataReader->readUint32(); pPathNode_Fastman92->m_extended_posn.z = pDataReader->readUint32(); } for (uint32 i = 0, j = m_header.m_uiNaviNodeCount; i < j; i++) { CDATEntry_Paths_Fastman92_NaviNode_extended *pNaviNode_Fastman92 = pNaviNodes + i; pNaviNode_Fastman92->posX = pDataReader->readUint16(); pNaviNode_Fastman92->posY = pDataReader->readUint16(); pNaviNode_Fastman92->info.areaId = pDataReader->readUint16(); pNaviNode_Fastman92->info.nodeId = pDataReader->readUint16(); pNaviNode_Fastman92->dirX = pDataReader->readUint8(); pNaviNode_Fastman92->dirY = pDataReader->readUint8(); pNaviNode_Fastman92->m_dwFlags = pDataReader->readUint32(); pNaviNode_Fastman92->extended_posX = pDataReader->readUint32(); pNaviNode_Fastman92->extended_posY = pDataReader->readUint32(); } for (uint32 i = 0, j = m_header.m_uiLinkCount; i < j; i++) { CDATEntry_Paths_Fastman92_Link *pLink_Fastman92 = pLinks + i; pLink_Fastman92->m_usAreaId = pDataReader->readUint16(); pLink_Fastman92->m_usNodeId = pDataReader->readUint16(); } if (m_header.m_uiLinkCount > 0) { string strFiller1 = pDataReader->readString(768); } for (uint32 i = 0, j = m_header.m_uiLinkCount; i < j; i++) { CDATEntry_Paths_Fastman92_NaviLink *pNaviLink_Fastman92 = pNaviLinks + i; pNaviLink_Fastman92->m_uiData = pDataReader->readUint32(); } for (uint32 i = 0, j = m_header.m_uiLinkCount; i < j; i++) { CDATEntry_Paths_Fastman92_LinkLength *pLinkLength_Fastman92 = pLinkLengths + i; pLinkLength_Fastman92->m_ucLength = pDataReader->readUint8(); } for (uint32 i = 0, j = m_header.m_uiLinkCount; i < j; i++) { CDATEntry_Paths_Fastman92_PathIntersectionFlags *pPathIntersectionFlags_Fastman92 = pPathIntersectionFlags + i; uint8 ucByte = pDataReader->readUint8(); //pPathIntersectionFlags_Fastman92->m_bRoadCross = ucByte & 1; //pPathIntersectionFlags_Fastman92->m_bPedTrafficLight = ucByte & 2; pPathIntersectionFlags_Fastman92->m_ucData = ucByte; } if (m_header.m_uiLinkCount > 0) { string strFiller2 = pDataReader->readString(192); } if (m_header.m_uiLinkCount > 0) { string strFiller3 = pDataReader->readString(192); } string strEOF = pDataReader->readString(4); // //if (strEOF.substr(0, 3) != "EOF") //{ //CDebugger::log("PARSER FAILED on index " + CStringUtility::toString(pDATFile_Paths->m_uiFileIndex) + ", bytes read: " + CStringUtility::toString(pDataReader->getByteCountRead())); //} // // -- for (uint32 i = 0, j = m_header.m_uiPathNodeCount; i < j; i++) { CDATEntry_Paths_Fastman92_PathNode_extended &pPathNode_Fastman92 = *(pPathNodes + i); CDATEntry_Paths_General_PathNode &pPathNode_General = m_vecPathNodes[i]; pPathNode_General.m_bIsVehiclePathNode = i < m_header.m_uiVehicleNodeCount; pPathNode_General.m_pPrev = 0; pPathNode_General.m_ppNext = 0; pPathNode_General.m_vecPosition.x = pPathNode_Fastman92.m_extended_posn.x; pPathNode_General.m_vecPosition.y = pPathNode_Fastman92.m_extended_posn.y; pPathNode_General.m_vecPosition.z = pPathNode_Fastman92.m_extended_posn.z; pPathNode_General.m_wSearchList = pPathNode_Fastman92.m_wSearchList; pPathNode_General.m_wConnectedNodesStartId = pPathNode_Fastman92.m_wConnectedNodesStartId; pPathNode_General.m_wAreaId = pPathNode_Fastman92.m_wAreaId; pPathNode_General.m_wNodeId = pPathNode_Fastman92.m_wNodeId; pPathNode_General.m_ucPathWidth = pPathNode_Fastman92.m_nPathWidth; pPathNode_General.m_ucNodeType = pPathNode_Fastman92.m_nNodeType; pPathNode_General.m_uiFlags = pPathNode_Fastman92.m_dwFlags; } for (uint32 i = 0, j = m_header.m_uiNaviNodeCount; i < j; i++) { CDATEntry_Paths_Fastman92_NaviNode_extended &pNaviNode_Fastman92 = *(pNaviNodes + i); CDATEntry_Paths_General_NaviNode &pNaviNode_General = m_vecNaviNodes[i]; pNaviNode_General.m_iPosition[0] = pNaviNode_Fastman92.extended_posX; pNaviNode_General.m_iPosition[1] = pNaviNode_Fastman92.extended_posY; pNaviNode_General.m_usTargetNode_AreaId = pNaviNode_Fastman92.info.areaId; pNaviNode_General.m_usTargetNode_NodeId = pNaviNode_Fastman92.info.nodeId; pNaviNode_General.m_ucDirection[0] = pNaviNode_Fastman92.dirX; pNaviNode_General.m_ucDirection[1] = pNaviNode_Fastman92.dirY; pNaviNode_General.m_uiFlags = pNaviNode_Fastman92.m_dwFlags; } for (uint32 i = 0, j = m_header.m_uiLinkCount; i < j; i++) { CDATEntry_Paths_Fastman92_Link &pLink_Fastman92 = *(pLinks + i); CDATEntry_Paths_Fastman92_NaviLink &pNaviLink_Fastman92 = *(pNaviLinks + i); CDATEntry_Paths_Fastman92_LinkLength &pLinkLength_Fastman92 = *(pLinkLengths + i); CDATEntry_Paths_Fastman92_PathIntersectionFlags &pPathIntersectionFlags_Fastman92 = *(pPathIntersectionFlags + i); CDATEntry_Paths_General_Link &pLink_General = m_vecLinks[i]; pLink_General.m_usAreaId = pLink_Fastman92.m_usAreaId; pLink_General.m_usNodeId = pLink_Fastman92.m_usNodeId; pLink_General.m_usNaviNodeId = pNaviLink_Fastman92.m_uiData & 0xFFFF; // lower 16 bits pLink_General.m_usNaviAreaId = (pNaviLink_Fastman92.m_uiData >> 16) & 0xFFFF; // upper 16 bits pLink_General.m_ucLength = pLinkLength_Fastman92.m_ucLength; uint8 ucByte = 0; //ucByte |= pPathIntersectionFlags_Fastman92.m_bRoadCross ? 1 : 0; //ucByte |= pPathIntersectionFlags_Fastman92.m_bPedTrafficLight ? 2 : 0; pLink_General.m_ucPathIntersectionFlags = pPathIntersectionFlags_Fastman92.m_ucData; } /* // debug for (auto& pathNode : m_vecPathNodes) { CDebugger::log( "[path node]" + string(" position: ") + CStringUtility::toString((float32)((float32)pathNode.m_vecPosition.x / 8.0)) + " " + CStringUtility::toString((float32)((float32)pathNode.m_vecPosition.y / 8.0)) + " " + CStringUtility::toString((float32)((float32)pathNode.m_vecPosition.z / 8.0)) + " " + " search list: " + CStringUtility::toString(pathNode.m_wSearchList) + " first link id: " + CStringUtility::toString(pathNode.m_wConnectedNodesStartId) + " area id: " + CStringUtility::toString(pathNode.m_wAreaId) + " node id: " + CStringUtility::toString(pathNode.m_wNodeId) + " path width: " + CStringUtility::toString(pathNode.m_ucPathWidth) + " node type: " + CStringUtility::toString(pathNode.m_ucNodeType) + " flags: " + CStringUtility::toString(pathNode.m_uiFlags) ); } for (auto& naviNode : m_vecNaviNodes) { CDebugger::log( "[navi node]" + string(" position: ") + CStringUtility::toString((float32)((float32)naviNode.m_iPosition[0] / 8.0)) + " " + CStringUtility::toString((float32)((float32)naviNode.m_iPosition[1] / 8.0)) + " " + " area id: " + CStringUtility::toString(naviNode.m_usTargetNode_AreaId) + " node id: " + CStringUtility::toString(naviNode.m_usTargetNode_NodeId) + " direction x: " + CStringUtility::toString(naviNode.m_ucDirection[0]) + " direction y " + CStringUtility::toString(naviNode.m_ucDirection[1]) + " flags: " + CStringUtility::toString(naviNode.m_uiFlags) ); } */ // clean up delete[] pPathNodes; delete[] pNaviNodes; delete[] pLinks; delete[] pNaviLinks; delete[] pLinkLengths; delete[] pPathIntersectionFlags; }
void CCOLEntry::unserialize(void) { CDataReader *pDataReader = CDataReader::getInstance(); uint32 uiHeaderStartPosition = pDataReader->getSeek(); setHeaderStartOffset(uiHeaderStartPosition); // COL 1 2 3 & 4 header setCOLVersion(CCOLManager::getCOLVersionFromFourCC(pDataReader->readString(4))); if (getCOLVersion() == nullptr) { throw EXCEPTION_UNKNOWN_FORMAT; } uint32 uiEntrySize = pDataReader->readUint32(); // entry size from after this value setModelName(CStringUtility::rtrimFromLeft(pDataReader->readString(22))); setModelId(pDataReader->readUint16()); parseBoundingObjects(); eCOLVersion eCOLVersionValue = getCOLVersion() == nullptr ? COL_UNKNOWN : getCOLVersion()->getVersionId(); if (eCOLVersionValue == COL_1) { // COL 1 header & body // read collision sphere count setCollisionSphereCount(pDataReader->readUint32()); // read collision spheres array setCollisionSpheresOffset(pDataReader->getSeek()); parseCollisionSpheres(); // read unknown1 count setUnknown1(pDataReader->readUint32()); // number of unknown data (0) // read collision box count setCollisionBoxCount(pDataReader->readUint32()); // read collision boxes array setCollisionBoxesOffset(pDataReader->getSeek()); parseCollisionBoxes(); // read collision mesh vertex count setCollisionMeshVertexCount(pDataReader->readUint32()); // read collision mesh vertices array setCollisionMeshVerticesOffset(pDataReader->getSeek()); parseCollisionMeshVertices(); // read collision mesh face count setCollisionMeshFaceCount(pDataReader->readUint32()); // read collision mesh faces array setCollisionMeshFacesOffset(pDataReader->getSeek()); parseCollisionMeshFaces(); } else { // COL 2 3 & 4 header setCollisionSphereCount(pDataReader->readUint16()); setCollisionBoxCount(pDataReader->readUint16()); setCollisionMeshFaceCount(pDataReader->readUint16()); setCollisionConeCount(pDataReader->readUint8()); uint8 ucPadding1 = pDataReader->readUint8(); // 1 byte padding setFlags(pDataReader->readUint32()); setCollisionSpheresOffset(pDataReader->readUint32()); setCollisionBoxesOffset(pDataReader->readUint32()); setCollisionConesOffset(pDataReader->readUint32()); setCollisionMeshVerticesOffset(pDataReader->readUint32()); setCollisionMeshFacesOffset(pDataReader->readUint32()); setTrianglePlanesOffset(pDataReader->readUint32()); if ((getFlags() & 8) != 0) { // entry does have face groups uint32 uiCurrentSeek = pDataReader->getSeek(); // read face group count uint32 uiFaceGroupCountSeek = (getHeaderStartOffset() + 4 + getCollisionMeshFacesOffset()) - 4; pDataReader->setSeek(uiFaceGroupCountSeek); setCollisionMeshFaceGroupCount(pDataReader->readUint32()); // read face groups offset setCollisionMeshFaceGroupsOffset((getCollisionMeshFacesOffset() - 4) - (28 * getCollisionMeshFaceGroupCount())); // 28 = sizeof(TFaceGroup) // restore parser seek position pDataReader->setSeek(uiCurrentSeek); } else { // entry does not have face groups setCollisionMeshFaceGroupCount(0); setCollisionMeshFaceGroupsOffset(0); } if (eCOLVersionValue == COL_3 || eCOLVersionValue == COL_4) { // COL 3 & 4 header setShadowMeshFaceCount(pDataReader->readUint32()); setShadowMeshVerticesOffset(pDataReader->readUint32()); setShadowMeshFacesOffset(pDataReader->readUint32()); if (eCOLVersionValue == COL_4) { // COL 4 header setUnknown1(pDataReader->readUint32()); } } // calculate vertex counts // COL 2 3 & 4 uint32 uiCollisionMeshVertexCount = calculateCollisionMeshVertexCount(); setCollisionMeshVertexCount(uiCollisionMeshVertexCount); if (eCOLVersionValue == COL_3 || eCOLVersionValue == COL_4) { // COL 3 & 4 uint32 uiShadowMeshVertexCount = calculateShadowMeshVertexCount(); setShadowMeshVertexCount(uiShadowMeshVertexCount); } // COL 2 3 & 4 body pDataReader->setSeek(getHeaderStartOffset() + 4 + getCollisionSpheresOffset()); parseCollisionSpheres(); pDataReader->setSeek(getHeaderStartOffset() + 4 + getCollisionBoxesOffset()); parseCollisionBoxes(); pDataReader->setSeek(getHeaderStartOffset() + 4 + getCollisionMeshVerticesOffset()); parseCollisionMeshVertices(); pDataReader->setSeek(getHeaderStartOffset() + 4 + getCollisionMeshFaceGroupsOffset()); parseCollisionMeshFaceGroups(); pDataReader->setSeek(getHeaderStartOffset() + 4 + getCollisionMeshFacesOffset()); parseCollisionMeshFaces(); if (eCOLVersionValue == COL_3 || eCOLVersionValue == COL_4) { // COL 3 & 4 body pDataReader->setSeek(getHeaderStartOffset() + 4 + getShadowMeshVerticesOffset()); parseShadowMeshVertices(); pDataReader->setSeek(getHeaderStartOffset() + 4 + getShadowMeshFacesOffset()); parseShadowMeshFaces(); } } if (!pDataReader->canSeekTo(getHeaderStartOffset() + uiEntrySize + 8)) { // EOF return; } pDataReader->setSeek(getHeaderStartOffset() + uiEntrySize + 8); }