A 2D tile-based sandbox game.
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

TileAtlas.cc 1.6KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364
  1. #include "TileAtlas.h"
  2. #include <iostream>
  3. #include <vector>
  4. #include <algorithm>
  5. #include <stdio.h>
  6. #include <string.h>
  7. #include <swan-common/constants.h>
  8. #include "gl.h"
  9. namespace Cygnet {
  10. struct AtlasState {
  11. size_t tilesPerLine;
  12. size_t width = 0;
  13. size_t height = 0;
  14. std::vector<unsigned char> data;
  15. };
  16. TileAtlas::TileAtlas(): state_(std::make_unique<AtlasState>()) {
  17. GLint size;
  18. glGetIntegerv(GL_MAX_TEXTURE_SIZE, &size);
  19. state_->tilesPerLine = std::min(size / SwanCommon::TILE_SIZE, 256);
  20. }
  21. TileAtlas::TileAtlas(TileAtlas &&) = default;
  22. TileAtlas::~TileAtlas() = default;
  23. void TileAtlas::addTile(size_t tileId, const void *data) {
  24. const unsigned char *bytes = (const unsigned char *)data;
  25. size_t x = tileId % state_->tilesPerLine;
  26. size_t y = tileId / state_->tilesPerLine;
  27. std::cerr << "Tile " << tileId << " to " << x << ", " << y << '\n';
  28. if (state_->width <= x) {
  29. state_->width = x + 1;
  30. }
  31. if (state_->height <= y) {
  32. state_->height = y + 1;
  33. }
  34. size_t requiredSize = state_->tilesPerLine * SwanCommon::TILE_SIZE *
  35. state_->height * SwanCommon::TILE_SIZE * 4;
  36. state_->data.resize(requiredSize);
  37. for (size_t ty = 0; ty < SwanCommon::TILE_SIZE; ++ty) {
  38. const unsigned char *src = bytes + ty * SwanCommon::TILE_SIZE * 4;
  39. unsigned char *dest = state_->data.data() +
  40. (y * SwanCommon::TILE_SIZE + ty) * state_->tilesPerLine * SwanCommon::TILE_SIZE * 4 +
  41. (x * SwanCommon::TILE_SIZE * 4);
  42. memcpy(dest, src, SwanCommon::TILE_SIZE * 4);
  43. }
  44. }
  45. const unsigned char *TileAtlas::getImage(size_t *w, size_t *h) {
  46. *w = state_->tilesPerLine * SwanCommon::TILE_SIZE;
  47. *h = state_->height * SwanCommon::TILE_SIZE;
  48. return state_->data.data();
  49. }
  50. }