tmxlite
tmxlite copied to clipboard
I need to use this in a std::map but am being prevented by operator deletion
I'm using a manager to store my game maps. The code is similar to this.
//_maps is an std::map. name is a string
tmx::Map _map
MapManager::_maps[name] = _map;
Fails because of operator deleted. So I got rid of that code and am directly storing maps in my game controller. However, I cannot keep loading the map each cycle as that is cpu intensive. I therefore tried to place the maps as private values in the controller but I get this error.
[5/9038]
./include/playing.h:14:18: note: copy constructor of 'PlayController' is implicitly deleted because field '_outerWorld' has a deleted
copy constructor
tmx::Map _outerWorld;
./include/tmxlite/Map.hpp:96:9: note: 'Map' has been explicitly marked deleted here
Map(const Map&) = delete;
How can I get around this? I tried deleting the Map code but it leads to even more errors. Note std::map insert does not work for some reason
My bad, Map was missing its move assignment / move constructor. I've updated the the repository and you can now do
_maps.emplace("map_name", tmx::Map());
or
_maps["map_name"] = tmx::Map();
Ok it works now. Thanks very much.
The problem is also evident in MapLayer but I managed to fix it by using the code you added for Map.
Ok MapLayer still doesnt work
What is 'MapLayer'? There is ImageLayer
, TileLayer
and ObjectGroup
all of which inherit Layer
. The vector of layers in the Map
class contains unique_ptrs which will make it inherently non-copyable. Perhaps you should think of tmx::Maps like other resources such as textures or shaders - load them once into your std::map/resource holder, then pass references to them around your program, avoiding any attempted copies.
No. I'm talking about MapLayer in SFMLOrthogonal. That's what I plan to do.
OK Sorry, I forget there were some examples :) To be honest I wouldn't use them in production code, they are merely there to demonstrate how you might make a drawable from a map layer using vertex arrays. For now you could temporarily remove the deleted constructor/assignment operator lines, although you may run in to other problems further down the line, but you'd at least be able to get something drawing. Vertex arrays are also notorious for the 'tearing' problem, so you may want to implement a renderer using this technique instead.
Oh, ok. Are there any prebuilt renderers I could use (compatible with this) or must I create my own?
Other than the examples I don't have any, but you may be able to find someone else using the library and ask them. The general idea is that the lib only parses tmx data into a C++ data format - what you do with the data is up to you, so it can be made to best suit your project.
Hey, I noticed in the SFML Orthogonal the tile map stops rendering past a certain distance when scaled.
Quite possibly related to #14 and #23
I think the problem is that I'm scaling 16 x 16 tiles to a SCALE variable. I'm not exactly sure how to fix this issue.
Ah - presumably you're applying the scale to the transform contained in the sf::RenderStates passed to the draw function? If this is the case updateView() will need the scale applied to it too, so that it's large enough to account for the scaled up chunk size (I think) or apply the scale to the chunksize value to get the appropriate count from the view
int posX = static_cast<int>(std::floor(viewCorner.x / (m_chunkSize.x * SCALE)));
int posY = static_cast<int>(std::floor(viewCorner.y / (m_chunkSize.y * SCALE)));
I've tried changing this but now it only renders about half of the map the turns white.
fallahn I'm really confused about this..
OK, based on what you've said the problem sounds like this: the example renderer is using the CPU bound tile coordinates of the map to calculate which tiles ought to be visible on screen. Then, when you apply a scale, things are drawn incorrectly. Bugs aside this sounds like it could be due to the fact that scale values passed via a transform are done GPU side, in what would be the fixed-function equivalent of the vertex shader stage. Technically this means that the CPU side calculations are incorrect relative to the output drawn on screen, because the scale is not taken into account when calculating the view. So what potential solutions are there?
-
Try compensating in the view calculation by including the scale. This was my above attempted solution, but without spending some time debugging it, I can't give a precise answer on how to make it work. If you study the code and work it out on some paper it's probably not as complicated as it looks.
-
Rather than apply scaling dynamically, prescale the assets in your art editor. I've done this in one of my own projects and it works well. Just remember when resizing images to set the mode to 'nearest neighbour' to prevent blurring from resize filters. It's probably also worth resizing to power of two numbers - in my case I went from 16x16 to 64x64.
-
Probably simpler to achieve than the first two: resize your view, effectively zooming in on the scene. For example set it to 1/4 the size of your screen. This means that without the transform scale the CPU/GPU numbers match up. This also applies the scale to the entire scene in one go without having to apply it to every drawable.
-
Create your own renderer. The example is just that, an example. It is also proven to be buggy so therefore far from being a magic bullet. I understand this feels like a PITA to do, but your own fully customised renderer will always be far superior. You can start by looking at the official SFML tutorial on creating a tile map. Looking at it you can see the core of the tile layout is merely an array of integers representing tile IDs - the first step would be to simply replace this with the tile IDs loaded with tmxlite, as well as using the file path property of the tile set to load the textures. Test this out, it may be all you need for your project. If it doesn't perform as well as you like, then it's time to consider a chunking strategy.
Hi,
Thanks for the detailed feedback. I think the smartest thing to do would be to resize the view.
Thanks fallahn.
So, the problem isn't with scale. TMXLITE is only loading half my tile map.
Could this have something to do with the fact that I'm instantiating a new tile layer every frame?
When you say only half do you mean it only loads 1 out of 2 layers? 4 out of 8? Or is it physically cut in half so a 128x128 tile layer only has 64x128 tiles loaded? Does drilling down through your debugger tell you what's missing? Or is the tmx file loaded, but a limitation in the renderer preventing all of it from being drawn? In general you would load the map once then use the loaded data to create a drawable (or more) for each layer, then repeatedly draw that each frame. You don't need to recreate anything - even if you were using animated sprites you only need to update texture coord data. Once the drawable has been created you can discard the tmx data
Or is the tmx file loaded, but a limitation in the renderer preventing all of it from being drawn?
I believe the issue is this