| 1527 | } |
| 1528 | |
| 1529 | bool LoadLevel(const std::string& path, bool partial) |
| 1530 | { |
| 1531 | FILE* filePtr = nullptr; |
| 1532 | bool loadedSuccessfully = false; |
| 1533 | |
| 1534 | try |
| 1535 | { |
| 1536 | filePtr = FileOpen(path.c_str()); |
| 1537 | |
| 1538 | if (!filePtr) |
| 1539 | throw std::exception{ (std::string{ "Unable to read level file: " } + path).c_str() }; |
| 1540 | |
| 1541 | char header[4]; |
| 1542 | unsigned char version[4]; |
| 1543 | int systemHash = 0; |
| 1544 | int levelHash = 0; |
| 1545 | |
| 1546 | // Read file header |
| 1547 | ReadFileEx(&header, 1, 4, filePtr); |
| 1548 | ReadFileEx(&version, 1, 4, filePtr); |
| 1549 | ReadFileEx(&systemHash, 1, 4, filePtr); |
| 1550 | ReadFileEx(&levelHash, 1, 4, filePtr); |
| 1551 | |
| 1552 | // Check file header. |
| 1553 | if (std::string(header) != "TEN") |
| 1554 | throw std::invalid_argument("Level file header is not valid! Must be TEN. Probably old level version?"); |
| 1555 | |
| 1556 | // Check level file integrity to allow or disallow fast reload. |
| 1557 | if (partial && levelHash != LastLevelHash) |
| 1558 | { |
| 1559 | TENLog("Level file has changed since the last load; fast reload is not possible.", LogLevel::Warning); |
| 1560 | partial = false; |
| 1561 | FreeLevel(false); // Erase all precached data. |
| 1562 | } |
| 1563 | |
| 1564 | // Store information about last loaded level file. |
| 1565 | LastLevelFilePath = path; |
| 1566 | LastLevelHash = levelHash; |
| 1567 | LastLevelTimestamp = std::filesystem::last_write_time(path); |
| 1568 | |
| 1569 | // Only check version if this is not a dummy level, because dummy level is rarely updated. |
| 1570 | if (path.find(DUMMY_LEVEL_NAME) == std::string_view::npos) |
| 1571 | { |
| 1572 | TENLog("Level compiler version: " + std::to_string(version[0]) + "." + std::to_string(version[1]) + "." + std::to_string(version[2]), LogLevel::Info); |
| 1573 | |
| 1574 | // Check if level version is higher than engine version |
| 1575 | auto assemblyVersion = TEN::Utils::GetProductOrFileVersion(true); |
| 1576 | for (int i = 0; i < assemblyVersion.size(); i++) |
| 1577 | { |
| 1578 | if (i >= 3) |
| 1579 | break; // Don't compare revision number. |
| 1580 | |
| 1581 | if (assemblyVersion[i] != version[i]) |
| 1582 | { |
| 1583 | TENLog("Level version is different from TEN version.", LogLevel::Warning); |
| 1584 | break; |
| 1585 | } |
| 1586 | } |
nothing calls this directly
no test coverage detected