125 lines
No EOL
3.7 KiB
C++
125 lines
No EOL
3.7 KiB
C++
#include "gameplay/map.h"
|
|
#include "gameplay/camera.h"
|
|
#include "graphics/shader.h"
|
|
#include "graphics/texture.h"
|
|
#include "utility/xmlloader.h"
|
|
#include "utility/resourcemanager.h"
|
|
#include "utility/logger.h"
|
|
|
|
#include <glm/gtc/matrix_transform.hpp>
|
|
|
|
Map::Map(std::shared_ptr<MapData> mapData, const unsigned shaderID, std::shared_ptr<ResourceManager> resourceManager) :
|
|
mapData(mapData),
|
|
tileIds(mapData->tiles)
|
|
{
|
|
this->shaderID = shaderID;
|
|
|
|
for (auto& tileSet : mapData->tileSets)
|
|
tileSetData.push_back(resourceManager->loadTileSet(tileSet.path));
|
|
|
|
if (!tileSetData.empty())
|
|
{
|
|
std::vector<const char*> buffer;
|
|
for (int layer = 0; layer < tileIds.size(); layer++)
|
|
{
|
|
buffer.clear();
|
|
for (auto& set : tileSetData)
|
|
buffer.push_back(set->file.c_str());
|
|
if (!buffer.empty())
|
|
instanceHandles.push_back(std::make_shared<TileTextureInstance>(buffer));
|
|
}
|
|
|
|
loadMap();
|
|
createCollisionMap();
|
|
}
|
|
|
|
}
|
|
#include <glm/ext.hpp>
|
|
void Map::loadMap()
|
|
{
|
|
tileData.resize(tileIds.size());
|
|
for (int layer = 0; layer < tileIds.size(); layer++)
|
|
{
|
|
for (int y = 0; y < tileIds[layer].size(); y++)
|
|
{
|
|
for (int x = 0; x < tileIds[layer][y].size(); x++)
|
|
{
|
|
glm::mat4 modelMatrix =
|
|
glm::translate(glm::mat4(1.f), glm::vec3(x * mapData->tileSize, y * mapData->tileSize, 0.0f)) *
|
|
glm::scale(glm::mat4(1.f), glm::vec3(mapData->tileSize, mapData->tileSize, 1.0f));
|
|
|
|
int textureIndex = static_cast<int>(getTileSetIndex(tileIds[layer][y][x]));
|
|
glm::vec2 originalSize = (textureIndex != -1) ?
|
|
glm::vec2(tileSetData[textureIndex]->width, tileSetData[textureIndex]->height) :
|
|
glm::vec2(0.0f);
|
|
int tilesPerRow = (textureIndex != -1) ? tileSetData[textureIndex]->columns : 0;
|
|
int startID = (textureIndex != -1) ? mapData->tileSets[textureIndex].startID : 0;
|
|
int tileIndex = tileIds[layer][y][x];
|
|
|
|
tileData[layer].push_back({modelMatrix, originalSize, tileIndex, textureIndex, tilesPerRow, startID});
|
|
}
|
|
}
|
|
instanceHandles[layer]->updateInstanceData(tileData[layer]);
|
|
}
|
|
glm::vec2 canvasSize = glm::vec2(instanceHandles[0]->getTextureArray()->getWidth(), instanceHandles[0]->getTextureArray()->getHeight());
|
|
editUniformOnce("uCanvasSize", canvasSize);
|
|
}
|
|
|
|
void Map::createCollisionMap()
|
|
{
|
|
// Match collisionMap to map size
|
|
collisionMap.resize(tileIds[0].size());
|
|
for (int y = 0; y < tileIds[0].size(); ++y)
|
|
{
|
|
collisionMap[y].resize(tileIds[0][y].size(), 0);
|
|
}
|
|
|
|
for (int layer = 0; layer < tileIds.size(); layer++)
|
|
{
|
|
for (int y = 0; y < tileIds[layer].size(); y++)
|
|
{
|
|
for (int x = 0; x < tileIds[layer][y].size(); x++)
|
|
{
|
|
int id = tileIds[layer][y][x];
|
|
size_t tileSetIndex = getTileSetIndex(id);
|
|
if (tileSetIndex == -1)
|
|
collisionMap[y][x] = 0;
|
|
else
|
|
{
|
|
int startID = mapData->tileSets[tileSetIndex].startID;
|
|
auto& tile = tileSetData[tileSetIndex]->tiles[id - startID];
|
|
if (!tile->walkable)
|
|
collisionMap[y][x] = 1;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
void Map::draw()
|
|
{
|
|
for (int layer = 0; layer < instanceHandles.size(); layer++)
|
|
{
|
|
instanceHandles[layer]->draw();
|
|
}
|
|
}
|
|
|
|
/*
|
|
Use this function to get the tileSetIndex from a tile ID.
|
|
the index of the tileSet is the same index as the texture index used in the instanceHandle
|
|
|
|
returns tileSetIndex of the tile id passed. Unless the id is either 0 or
|
|
the returned tileSetIndex is out of bounds, returns -1
|
|
*/
|
|
size_t Map::getTileSetIndex(int id) const
|
|
{
|
|
// work from the bottom, break if ID > startID
|
|
// If we get a textureIndex of -1 then we are on an empty tile
|
|
size_t tileSetIndex = mapData->tileSets.size() - 1;
|
|
for (; tileSetIndex != -1; --tileSetIndex)
|
|
{
|
|
if (id >= mapData->tileSets[tileSetIndex].startID)
|
|
break;
|
|
}
|
|
return (tileSetIndex >= mapData->tileSets.size()) ? -1 : tileSetIndex;
|
|
} |