Beta: Tile Map
As some of you might be aware, I've been busy for quite a while now - Which is mainly because of two things:
First of all, I'm in the middle of my final school exams - I should be studying right now but meh, and secondly, I've been really caught up with my current extension projects, all of which were requested, so I barely have time to work on anything else. My three biggest projects right now are Box2D (the flash port), OpenAL (sound extension with surround and effects and stuff), and the one I'm going to tell you about right now - Sorry for the long explanation of my situation :D
This extension is will be available in Flash - it will also support the standard runtime and it works in HWA (although, of course, not optimized) - What it does is basically render maps that are made up of tiles. There are two core entities: Tilesets, which each contain an image and some minor parameters such as tile spacing within the image, and layers, which contain a rectangular map area made up of tiles.
Layers each can have different scrolling speeds for parallax effects and the extension interacts with the MMF scrolling system quite well. You basically have a couple of layers, as many as you need - you could divide rooms into layers and give them different offsets, for example, or just use one huge layer for the foreground, and some for the background etc.
The point of this extension is efficiency. You can have a huge map, say, 1000x1000 tiles, with a tilesize of 32x32, and the app will still run at 500 fps at 640x480 in the standard runtime - my goal is to reach the very same performance in Flash, and there is a huge trick that allows me to do so: The map is stored as a huge grid, there is no "list of tiles", as there would be with levels made up of single Backdrop objects. And this is crucial. So basically, you will be able to create huge, detailed maps in Flash without having to worry that adding one more tile here and there will cause a slowdown, because only what is visible on the screen is even processed at all. I'm pretty confident that a game with a magnitude of Knytt would be possible in Flash with this extension. There will of course be support for collision detection, which we haven't exactly decided on yet - I will probably offer the standard "is overlapping" routines, and let you set a collision flag for each layer or so. Who knows! I just wanted to let you know that this extension is coming, and anybody who has planned to make a big game in Flash might want to consider it - but of course, small games are possible as well - For example, you can use the extension for wrapping layers (which are directly supported) or parallax effects, and there will be and already are some handy editing functions to fill the map with complex structures without a lot of hassle.
Woah, long post. Well, that's all I have to say for now - a screenshot will not reveal much, not even a program would, I suppose - So until the Flash runtime is working somewhat, I do not plan to release a preview of the extension because I can't use the feedback right now, there is so much in my head to change and add that half of the things you'd suggest would already be planned out anyway. I just felt like writing this post for you now, so if you're interested, keep coming back here to see if I made any progress. There's not really a need for you to comment, unless you have specific questions which I will be glad to answer - Thanks!
Ah what the hell: Here's a stupid screenshot that shows a 30,000 x 30,000 frame completely filled with tiles while I am moving around at 500 fps. http://i44.tinypic.com/34skrdc.png Just try to imagine that this will be amazing once it's ported to Flash :D
What can be said, Looki, besides YOU ARE AWESOME! You are a treasure to the Click community.
I hope that some day soon Spriter animations could be used along with your tile map extension to make drastically more powerful games and bigger game levels.
Been working on the Flash port and it's coming along nicely. Done some comparisons:
I set up a 30,000x30,000 frame again, with a tilesize of 24x24 that corresponds to 1250x1250 ~ 1.5 million tiles.
In Flash, even with 3 layers of this size, which is kind of ridiculous to have anyway, it runs at solid 60 fps on my machine.
Well.. and then I tried to replicate this scenario with Backdrop objects, like you kind of have to in the current Flash runtime, unless you use a super complex tile rendering system with various tricks, which no one does, I guess - after all, this is why the extension is in the works! So anyway, I kept duplicating a 'Tile' backdrop object, but MMF became so slow with 40,000 tiles (Mind you, that is 1/40 of what I rendered with Tile Map at no cost...). So I thought: Well, let's see how Flash performs. The result: 30 FPs when scrolling.
I hope this shows you the power of the extension: While MMF backdrops slow down your game piece by piece, Tile Map won't. Simple as that. I was able to have 40 times more tiles than with Backdrops, which MMF couldn't even handle anymore, but the extension could. I really don't want to waste time by making a nice demonstration SWF that shows the huge frame and that you can move around freely, just believe me :D
EDIT: Oh right, I used 3 layers with my extension, so of course thrice as many tiles, i.e. 120 times more tiles than the backdrop test. Woo.
This sounds like a really great extension, i am looking forward to testing it :)
This sounds like something I could use with my leveleditor to create really huge levels! I guess I would just read the levelcontent into the map extension instead of making everything actives which adds to backdrops.
Will the the condition IsBackdrop work with these backdrops produced by the extension, or maybe you could add a similar condition to the plugin?
Each of my tiles also create two extra non-obstacle backdrop objects, one at top of it and one at the right to make a 3D look for each tile, so it looks like any nintendo platform game. Would the extension be able to handle these objects also? I guess / hope that's what the layer system does, but I didn't totally grasp what you said about layers.
I don't plan to implement support for "is backdrop"; instead, the extension will have custom conditions for things like that. You can use layers to put multiple tiles above each other, not a problem!
Wow this is incredible news!!!! :D My biggest concern when I make something is always that it will run crappy in Flash, if this is as good as it sound it will be amazing!!! Is there any estimate when this will be finished? :) I dont want to stress you though! Just the thought of this coming is making me super happy right now! :D
And your continued work on the Box2D port for Flash is also great! It will be so nice when Flash in MMF have more support for the extensions and these performance boosts so you can actually develop for standard runtime with these extensions and not have to keep so much back because of uncompatible extensions or performance! :D
Btw, Popcorn, do you have an example of this IsBackdrop 3D tile effect? It sounds interesting :)
"Finished" - no idea. "Public beta that already works quite well" - soon ;) In a few days I would say.
Oh my oh my. This is an extension and a half. Nice one Looki, I can't wait!
This is amazing! I need to ask a few questions before I get too excited:
1) Does this tile extension allow for separate collision layers? Something like this, where the players interact on a different collision layer than the visible background image:
2) Can the tiles be placed above a moving active object? Either using an MMF layer or otherwise. Like this:
The tiles Wario walks on are in front of him and the Blocks.
3) Can I delete and re-add tiles at runtime? For example, in a game where tiles are destroyable, and the player can build Structures with various tiles. This is the main reason I use "Add Backdrop" for my current project - its easy to add/destroy tiles.
4) Does it support rectangular tiles? My current project uses tiles that aren't the same height and width.
All of these are necessary for my current project, and very important for most serious game projects. Regardless, this extension is extremely useful as is. I can't wait to play around with it.
I've moved this thread to the Ext Dev forum because the extension isn't Flash only. It just happens to support Flash. Btw, upcoming Beta soon. Because of personal reasons, this one will have no Flash though. I can't work on Flash at this workplace I'm afraid.
1) Yes - In fact, after discussing with some clickers, I've decided on a format: Basically, it's already there! You can just have an invisible layer, storing your collsiion tiles, and check for collision with it. That's it. Super flexible.
2) I've actually sent Yves a PM about this. I could implement this in Flash *easily*, but not in the EXE version. It'd require some hacking, I hope he can help. Nevertheless, I will offer this feature for Flash, even if I can't implement it like that in the EXE version. It's just a single property, anyway (render above player, yes or no). It is possible to put the Tile Map above an Active right now, but you can't do both behind and above at the same time with one instance. I might offer the ability to link a second Tile Map object to another one so it can render some layers above an Active.
3) Yes, that's one of the major advantages that I forgot to mention in my post :D You can do that of course.
I think you might like this extension :)
I'm changing things around right now - Me and Hempuli have been discussing quite a lot. Basically I've introduced the concept of per-layer tilesets. This basically means each layer has one basic tileset that you can use. We agreed that specifying a tileset ID for every single tile is an advanced feature and should not be needed by most of you. If you look at tile-based games, they're usually divided into rooms (map files) that each only use a single tileset, really. If you have anything to say against that, please do! :) You will be able to do this somehow, anyway. I might introduce a concept of "optional data" that each layer might have - such as an equivalent to 'Alterable values', per each tile, or, of course, a 'tileset ID' per tile. This means that you will be able to create a giant map with lots of different tilesets if you want to. It's just that it's not really something a well designed game usually needs, so we've decided that it shouldn't be a crucial feature of the extension!
What about Nifflas' method in Knytt Stories of having dual tileset data for transitioning screens?
...what about it? I don't think I will implement that into the extension, it's kind of specific, in my opinion.
How are you storing the data? I'm working on something similar in MMF2 (a level editor not an extension), and I have found that without resorting to tricks the file sizes can grow really big really fast. You mentioned having a level 30,000 pxls wide and tall (roughly 1000^2 tiles if I am guessing right). When I do that on a single layer I am getting file sizes of about a hundred Mb. I haven't tried with multiple layers yet, but it should be a linear progression.
So how big are your file sizes?
Wow! This would be great. I mean it would offer NEW possibilities!!! Time to get excited: NOW!!
Jakinbandw, I use zlib compression. An uncompressed, empty 2000x2000 map is 7.6 MB - One with 6/10 compression level is only 7.6 KB. Of course, compression will get worse once you actually fill the map. However, since maps often have larger areas where there's only one tile all over (like a ground), and repeating patterns such as walls, there still will be pretty good compression. I don't know what you're doing to get over 100 MB, that's crazy! Each tile has exactly 2 bytes, so it's kinda like width*height*2. The rest, such as the rest, file header etc., are negligible. Do the math: 2000*2000*2 = 8,000,000 ~= 8MB
I'm pretty sure his math is wrong, but for a different reason, as 30,000*30,000*2 = 1,800,000,000 bytes = 1,716.61377 megabytes. If he's only getting a hundred megs, he must have really good compression.
it's actually only 1000^2 points of data (that I am working with). Right now my personal one that I am working on has dropped it's size to 24,200kb when it is filled with a single type of tile. Zipping that shrinks it to 2,255kb. I suspect that I am getting file sizes much bigger than yours because I am using the named variable object. It allows me to do a cool trick where if a point of data is 0 it doesn't store it, thus 100000^2 tiles with only 4 of them not empty has the same file size as a file that only has 4 tiles with all 4 of them not empty. Also allows my lvl editor to be extra dynamic because I am not limited by array dimensions.
Anyway, glad to hear it has such a small file size. I can't wait to use it for my next project.
LB: I only have store 1000^2 points of data with my system, I am storing the ID of images that are 32^2 pixels. If I tried to store every pixel... well then there would be problems.
Ooh, okay. Named variables aren't really suited for these kinds of things, yes.
Here's the first beta! It comes with a couple of examples that should help you get started. All of them focus on specific things, but also teach you how to use the basic actions I think. As I said, no Flash this time.
Well, not much to say. Have fun with it. Find them dirty bugs. One thing you should know that as of now, the Tile Map is always fixed on the screen. In combination with the "Follow MMF camera" property, you can still use it for scrolling games, though! Still a lot to do and add, but it's already quite functional as of now. I'd go as far as saying you could create games with it -- but you shouldn't yet. Please be aware I might change some actions or so which would effectively break them in your MFAs and you need to replace them with the new ones.
Thanks to Hempuli for his wonderful Tileset in the Editor example ;) Hope it all works well.
Oh right, maybe some info on the limitations: You can't have more than 254x254 tiles in a tileset. You can't store more than 16 tilesets at edittime (should be enough), and the runtime limit is 100 (that seriously should be enough!).
Some general usage infos: Once you add a new layer or tileset per action, it is automatically selected and you can modify it with the corresponding actions. The "Tiles" sub-menu always refers to the tiles of the >current layer<.
Nice! It's working well, but how come on the level editor, when testing, the X coordinate doesn't update past half the screen? It collides correctly and shows the Y coordinate correctly, but it doesn't update the X after the middle of the screen. :\
Well, it doesn't work in MMF2Dev Build 253. It can't load the Tilemap.mfx
LB: OHH, sorry, that was me playing around with some settings. Basically the problem is that the frame is bigger than the screen and MMF follows the player. But Tile Map is fixed on-screen and "Follow MMF camera" is unchecked, so it won't move. Derp.
Gah, sorry! I compiled a debug version, you need a special debug runtime for that.
Originally Posted by Jakinbandw
I fixed both issues and uploaded a new version! Sorry.
Working great so far, Looki. I need to know if an object is not overlapping the tileset, but the overlap condition wouldn't negate. Will this be possible?
Oh right. I forgot about that, sure.
I think I will! Even with two instances of the object I'm sure it'll save memory compared to hundreds of "Add Backdrops."
Originally Posted by Looki
Oh no! This is exactly what I need! While I would normally agree that 1 tileset per layer is fine, my current project is a bit more advanced. Most games have level themes such as "forest" or "lava" which works fine with that method. My project treats tiles more like materials such as wood, steel, bedrock, coal, etc. These tiles need to be available across many level themes.
Originally Posted by Looki
So individual tile ID's is a must for me. :)
But you said that this should be possible with certain conditions, so I'll try it out first. I'll have to get back to it later because I'm not at my MMF workstation.
A thousand thank-you's for this amazing extension.
Cool :) Yves confirmed that it's pretty much impossible to draw over and below an Active in one object, so I'll try to add in some kind of way to link two Tile Maps together. This should be possible. You'll have to wait a while for the tileset ID thing, I guess!
Oh btw, the map format is not final. Maps you save right now probably won't be compatible with newer versions of the extension!
Note: I noticed that the extension performs badly in HWA - Please don't report this bug. I've fixed it (but only if you uncheck "transparent").
I have tested this now and it seems to work great so far and this will be very useful for any tile based games i make, thanks Looki. :D
Edit - I also like the idea about tile alterables/attributes so you could tag a certain tile as grass, sand or stone etc. That type of option would be great for RPG games where the battles depend on the tile.
I'm really loving it so far! I can really see the potential here. Writing a level editor in only a handful of lines is amazing. I wish I had this about a month ago. =P
You said that HWA works but is a little slow. I have another HWA problem.
With HWA on, the levels draw in black & white. Collisions don't work as well, and my little guy falls into oblivion. Everything works great in Standard mode though.
As for level format compatibility, why not allow the extension to save maps as bitmaps, like the old Doom games? I believe Grand Theft Auto used this method too. I'm currently using some Surface objects to save map data as PNG images, which I then send to my artist (on a Mac) who can edit the maps in Photoshop too. It uses the RGB data to represent tiles.
Red is the tile, Green is the tileset, and Blue is any other data. Thats the format I'm using right now.
PNG offers some of the best file compatibility across many OS and programs. Of course a proprietary compressed file format is most ideal for distribution, but during edit time (when the file format may change a lot) its good to have a common-ground format that is easily convertible.
The Tile IDs and HWA compatibility would be ideal, but no pressure or anything. Otherwise its perfect. I'll be messing around with this extension in my free time to see what I can do with it as it is.
Hmm, I will add Surface interaction, so you could basically use Surface to load and save image files.
I know collisions don't work in HWA, thanks. But that black & white issue seems odd - an MFA would be great, but HWA support isn't on top of my list right now :)
Oh no... I'm working on an identical extension to improve my map object.
Thankfully Looki has just eased your effort :)
Competition increases productivity! :D I hope to release a new beta soon... one with Flash. Still need some time though!
Implemented Surface interaction, btw. Saves me the trouble of having to implement features like Flood fill, line drawing etc. :D
Cant wait for the Flash version!
Flash will take a while I'm afraid. I'm currently unable to work with the necessary development software.
We've decided to split up the extension into two single ones:
The 'Tile Map', which handles all the data: You load map files, manage tilesets and the layers with their tiles.
And then there's the 'Tile Map Viewport', which is basically what Tile Map does as well, right now: Render the level. You attach a Viewport to a Tile Map to render its content. This has several advantages. It's better design. If an action is in the Tile Map object, you'll know that the setting will be stored in saved map files. Plus, you can do things like split-screen easily - or, as someone requested earlier, have a layer above and behind the player :) A beta should be coming within the next 24 hours.
I'm working on a similar engine at the moment. The limitations that I'm aware of are: tiles don't exist when they're off screen, so you can't test for enemy platform collisions or do enemy path-finding when they leave the screen... the enemy is basically frozen until they re-enter the game frame. And 2) You need to load the whole map and all textures into memory, which can become large in itself if you're trying to do something like a 2D Skyrim or Grand Theft Auto.
I'm working towards dynamically loading the map and new textures from hard drive files as the player approaches new zones, ie. I can store the whole map in 128x128 zones and load 4 of these zones on startup, placing the player in the centre of this 2x2 zone grid. Then I unload from the left and load to the right whenever the player walks 128 tiles from left to right... This is the only way I can picture a truly unlimited map with no load times... well, only limited by the hard drive space.
Any thoughts on implementing this?
Basically, I think that advanced programmers should be able to implement this themselves in the extension. You'll be able to "paste" map files into the current map. So you'd basically start off with an empty map and keep filling it. You can also load and unload tilesets at wish - so it should be possible. I can see why you want it, but it's not something that I want to spend time on, because it's a bit complicated, you know - and while I want this to be a cool extension, I can't spend that much time on features that I'm not being paid for :) Besides, you can load huge tile maps without having to worry about memory or anything... as I stated earlier. Even if you were to have maps as big as 2000x2000 tiles, you'd still be in an 8 MB range. And I dare say that MMF games eat quite a bit anyway. It's not the most efficient approach for sure, though.
Btw, JimJam, this one's for you <3
All older MFAs and saved tile map files are now broken.
More actions, specifically ones related to the "cursor". You can now exchange data with Surface, for example.
Changed file format, allows me to add stuff later without breaking compatibility.
Split up extension into two parts, data handling and viewport.
I'll make some new examples, I guess, but it shouldn't be too hard to get started.
Put an instance of both extensions into the frame.
Start of frame: Assign viewport (select the viewport object)
Then, all you need to do is add a layer and set tiles. The default tileset is 0, which is the first one - you can add them in the properties of the Tile Map extension or load them manually via actions. Hope this was enough to get started!
Collision issues when having 2 instances of a viewport object