1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183
|
/*
* TMXCopy
* Copyright (C) 2007 Philipp Sehmisch
* Copyright (C) 2009 Steve Cotton
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include <string>
#include <vector>
#include <set>
#include <map>
#include <libxml/parser.h>
struct ConfigurationOptions
{
/* When copying map layers, how to match source layer to
* destination layer.
*
* True: Pair the first layer to the first layer, the second
* to the second, etc.
*
* False: Pair up layers with matching names.
*/
bool copyLayersByOrdinal;
/* Create extra layers in the target as necessary. */
bool createMissingLayers;
};
struct Tileset
{
std::string imagefile;
int firstgid;
std::string name;
int tilewidth;
int tileheight;
bool operator== (Tileset const& a)
{
return (imagefile == a.imagefile &&
tilewidth == a.tilewidth &&
tileheight == a.tileheight
);
}
Tileset()
{
}
Tileset(const Tileset& src) :
imagefile(src.imagefile), firstgid(src.firstgid),
name(src.name),
tilewidth(src.tilewidth), tileheight(src.tileheight)
{
}
};
/**
* A tile in a layer of a map.
*
* With the exception of the emptyTile and empty() function,
* interpreting what this tile represents depends on the map it
* belongs to (specifically the ordering of that map's tilesets).
*/
struct Tile
{
int tileset; // number of tileset
size_t index; // index in said tileset
bool empty()
{
return (tileset == -1);
}
/* This is to allow std::map<Tile,Tile> */
bool operator< (const Tile& b) const
{
return ((tileset < b.tileset) ||
((tileset == b.tileset) && (index < b.index)));
}
bool operator!= (const Tile& b) const
{
return ((tileset != b.tileset) || (index != b.index));
}
};
typedef std::vector<Tile> LayerTiles;
/* This represents an empty tile in the layer.
* Note that {0,0} would be the first tile in the first tileset.
*/
const Tile emptyTile = {-1, 0};
class Layer
{
public:
/* name - the name of the layer, as shown in Tiled
* tileCount - total number of tiles (width*height)
*/
Layer(std::string name, LayerTiles::size_type tileCount)
: mTiles(tileCount, emptyTile),
mName (name)
{
}
std::string getName() { return mName; }
Tile& at(LayerTiles::size_type c) { return mTiles.at(c); }
Tile& getTile(int x, int y, int mapWidth) { return mTiles.at(x + y*mapWidth); }
private:
LayerTiles mTiles;
std::string mName;
};
class Map
{
public:
Map(std::string filename);
~Map();
/**
* Copies an area from srcMap, replacing its current contents.
*/
bool overwrite(Map* srcMap,
int srcX, int srcY, int srcWidth, int srcHeight,
int destX, int destY,
const ConfigurationOptions& config);
/**
* Fills an area of this map with random parts of the template.
* Currently, each layer of the template is treated as an object that
* should be copied in its entirity.
*/
bool randomFill(Map* templateMap, const std::string& destLayerName,
int destX, int destY, int destWidth, int destHeight,
const ConfigurationOptions& config);
/**
* Translates a layer - using the template, generates collision from visible layers (for example).
* TODO - avoid confusion with the geometry term "translate"
*/
bool translateAllLayers(Map* templateMap, const std::string& destLayerName,
const ConfigurationOptions& config);
int save(std::string filename);
size_t getNumberOfLayers() { return mLayers.size(); }
Layer* getLayer(size_t num) { return mLayers.at(num); }
Layer* getLayer(std::string name);
std::vector<Tileset*>* getTilesets() { return &mTilesets; }
int getWidth() { return mWidth; }
int getHeight() { return mHeight; }
private:
std::map<int, int> addAndTranslateTilesets(const Map* srcMap);
std::vector<Layer*> mLayers;
int mWidth;
int mHeight;
int mMaxGid;
std::vector<Tileset*> mTilesets;
xmlDocPtr mXmlDoc;
};
|