Jump to content

Something small to do for me (that isn't being done by Heron)?


Recommended Posts

Hello - nice to see you around again :)

About the terrain painting: Um, yeah, that's not quite fixed yet :P. Not sure when you last looked at it - Atlas gives users more control over texture priority (left click to paint 'over' the surrounding tiles, right click for 'under') so a single texture no longer has a constant priority, and I think there were some tweaks to the renderer some years ago so that that worked more reliably, but it's still possible to get sharp edges where the wrong blend texture is used. (Some old examples/discussion here.)

There's some things in Trac - I assume you're still mostly interested in graphics, so I see some potentially useful ones like terrain triangulation, terrain decals (I think this is mainly required for farms (though useful for other effects), like in the front and back here, which should have a texture flat against the terrain but probably not constrained to grid squares, and ideally the crop meshes should adjust to non-flat terrain too; hopefully that'd help bugs like this), a desire for randomised terrain blends (preferably pseudo-random and deterministic) (I think the "chunky" problem there isn't a graphics problem, it's just unintuitive UI in Atlas), fixing transparent objects with water, adding fog. And more!

Link to post
Share on other sites

Ykkrosh, hello :)

Think I last looked at the terrain painting sometime around 2004, so might be a little rusty. Be a nice thing to fix, but I suspect it'll take quite a bit of thinking to get right. I've got the source downloaded, so I'll have a tinker around and see if I can get anywhere.

Link to post
Share on other sites

Yeah, as far as I'm aware it's not theoretically impossible with the current rendering system but I never managed to work out the logic to make it work. Let me know if you have any questions with building or running or following the code :). (It has changed a bit since 2004, though sadly not as much as one might hope...)

Link to post
Share on other sites

Got Atlas up and running this afternoon without any major problems (except wxWidgets refusing to believe wxUSE_GLCANVAS was set to 1). Also managed to duplicate the issue fairly easily; don't think it'll be quite so easy to prove it's actually fixed, sadly.

Will report back when either (a) I've made progress, or (:) decided it's too hard and given up.

Link to post
Share on other sites

I wonder if you could just test every possible combination. Each tile is only influenced by its 8 neighbours, and for each tile the texture is either new or the same as another's, so I think that's this sequence and with n=9 there's only 21147 texture combinations; and each tile can have a priority that's equal or different to the others, and it's a total order, so I think that's this and with n=9 there's 7087261 orderings, so you just multiply that by the texture combinations and get ...

Okay, maybe that's not going to work.

Link to post
Share on other sites

Hmm, that's quite a lot of cases. Glad I'm not a member of the test team.

Was trying to work out if I could somehow automate testing. Found the majority of visual errors are caused when two adjacent tiles can't work out the blending they're supposed to do, based on other surrounding tiles. I'm seeing cases where two tiles on an edge both think they should overlap the other, which obviously isn't correct, and could be found simply by storing which blendshape each tile/texture combination is using.

Fortunately, I can find errors without having to bother doing that - might investigate how useful it is later. I've found and fixed a few small issues which improve what happens presently, but it's still easy to break. In the two texture case, issues tend to occur iff texture A has tiles with priorities both higher and lower than an adjacent tile with texture B (this is probably why ScEd was a little more robust, using one priority per texture). In this case, I don't think it's sufficient for a tile just to look at it's neighbours to work out how to blend - it needs to look to see how it's neighbours are blending their own neighbours. All horribly recursive: my new fangled - still broken - system, allows you to paint in one corner of the world and magically update the blending in the other.

I'm umm-ing and ahh-ing over a couple of ideas for exploration:

1. More intelligent priority assignment: rather than blindly assigning priorities, look at the current priorities, and those of neighbouring tiles, and adjust things up as we go.

2. Modifying the current system to hold a list of textures applied to the terrain. If a tile is completely overwritten, replace the texture on that tile, otherwise, append to a list of textures on the tile (and which part of the tile (ie which alphamap is required)). Then, to render, just render the base texture stored in the tile, and apply any partial textures that have been applied to it.

#1 I'm not sure on; I'd guess you could get more "intelligent" terrain painting behaviour with some work, but whether it'd eliminate errors, I'm not sure.

#2 could possibly take up lots of fill rate, if artists use lots of textures per tile (but optimising that could easily be done later, some preprocess step before data gets packaged or whatever), but should be fairly trivial to implement.

I also found this, which has been published since I last investigated this. I've - ahem - only looked at the pictures, but seems to give better results on close-ups than the simple linear blending we use. Have to read the thing to determine whether it's worth further investigation.

Link to post
Share on other sites
this is probably why ScEd was a little more robust, using one priority per texture
Mixing priorities does make it more complex, but I think it's probably worthwhile - it gives more control to scenario designers, it avoids the complexity of having an external data file to specify the relative priorities of all terrain textures (or the arbitrariness of basing priorities on filename), and it almost works fine in the renderer.
paint in one corner of the world and magically update the blending in the other
Hmm, that's probably not so good - I think we'll want to be able to change terrain at runtime (like when you construct buildings and it draws a buildingy texture underneath), so changes should be reasonably efficient and visually localised.

It's possible the requirements are over-constrained and make a solution impossible, but I still can't see why it should be :)

The problem reminds me of polygon z-sorting, since there's one polygon (/set of tiles with the same texture) partly in front of and partly behind another, which makes me wonder if it's possible or useful to effectively split the first polygon into two so that there's a consistent ordering. But I don't know if that even makes sense...

I suppose I can imagine a situation like:

a B
a B
A b
A b

where each letter is a tile, a/A is one texture, b/B is another, uppercase is higher priority than lowercase. For the top row and bottom row, we just use blendedge (and flip one of them) to draw one texture on top of the other, so that's fine. But for the middle rows, it looks we don't have any set of blend shapes that can join the two outer rows smoothly. So we really do need to split the aaAA column into two splats, rather than treating it as one because it's all the same texture. I think. Still don't see the solution, though.

Link to post
Share on other sites

Ah, good work, Ykkrosh! Z-sorting analogy spot on, never thought of that Will see if that opens up any new avenues for exploration.

Instinctively, I do agree that the current system should work as is (ie no enduser changes required), although no idea why I think that - guess it just looks/feels close to final.

{ By the way, in case you're expecting rapid progress on this: my availability is a little limited, especially at weekends .. and, er, usually during the week too .. figure this isn't on any kind of critical must-fix list right now, though, so I'll just tinker away until someone pokes me into action :) }

Link to post
Share on other sites

(By the way, currently Atlas (in the TerrainHandlers.cpp code) gives each tile a priority that's unique amongst its neighbours, but it seems fairly easy to change it to prefer to share priority with existing neighbours if they're the same texture as this new tile and are already higher/lower priority than all other neighbours. That would prevent some of the common cases where priorities are unnecessarily varying, so it might usefully mitigate the problem, though it wouldn't solve the worst-case errors and they'd still need to be handled somehow.)

{ I think we do need to fix this eventually, but it's not critical by itself and it's not blocking any other work, so no urgency is required :). It's been a niggle for years so it'd be nice to get it out the way, though. }

Link to post
Share on other sites

Rich! Nice to see you on the forums :) Perhaps this is relevant, perhaps not.

Something I noticed about terrain painting was that it seemed that the smallest paintbrush you could use painted a 'tile' then overlapped to the 8 adjacent tiles bordering it (I'm not 100% sure atlas still does this?). Example:

2 2 2 2 2

2 ½ ½ ½ 2

2 ½ 1 ½ 2

2 ½ ½ ½ 2

2 2 2 2 2

vs.

2 2 2 2 2

2 2 2 2 2

2 2 ½ 2 2

2 2 2 2 2

2 2 2 2 2

So as you drag the paintbrush down across the tiles it does this:

2 2 2 2 2

2 ½ ½ ½ 2

2 ½ 1 ½ 2

2 ½ 1 ½ 2

2 ½ 1 ½ 2

vs.

2 2 2 2 2

2 2 2 2 2

2 2 ½ 2 2

2 2 ½ 2 2

2 2 ½ 2 2

The later gives the map maker more control over the terrain textures.

Check out the snapshot taken from AOM here:

http://trac.wildfiregames.com/wiki/ArtDesi...t#TerrainBlends

I'm also noticing however that the blend template below this screenshot doesn't have a completely captured 'spot' tile though.

It is also odd that AOM seems to allow 3 textures to be painted into one tile. I'm not sure how that works either...

Link to post
Share on other sites

Hmm, I might be completely wrong and you ought to know what you're talking about, so don't take this as anything else than a question: Are you sure that's from AoM? Because it looks like it could just as likely be from Atlas :) I'm mostly curious though, especially since your comment is still valid :)

I can confirm that Atlas does treat a one tile brush the way you describe.

Link to post
Share on other sites

In Atlas, use the right mouse button when painting terrain to make it go 'under' the surrounding tiles instead of over. And set the brush size to 0 if you want to draw the tiniest little bit. That should let you draw half-tiles.

(I suppose it's a bug that the brush display vanishes when you set the size to 0, but it still draws. I think there's also a problem that the brushes were designed for altering vertices, but terrain textures apply to tiles, so there's a half-tile offset.)

It is also odd that AOM seems to allow 3 textures to be painted into one tile.
The image actually has four textures on one tile, where the black+grey+grass+lava meet. I think you ought to be able to get nine on one tile, if you use a different texture per tile and the middle one is the lowest priority.

Does AoM have hard-coded texture priorities? i.e. you can draw a half-tile-wide strip of black stuff on top of grass, but can you draw half-tile-wide grass on top of the same black stuff?

Link to post
Share on other sites
Does AoM have hard-coded texture priorities?
Yes it does, seemingly. A one-tile strip of rock on grass appears half a tile wide, a one-tile strip of grass on rock appears two tiles wide. Atlas gives you more control since you can choose the in-front and behind behaviour in both cases. (But, Atlas does cause these rendering glitches.)

(Also in that screenshot, AoM does let you have a lot more than 3 textures on one tile; our game does the same.)

Link to post
Share on other sites

Yeah, it'd be good to have more documentation of the features and make it reasonably findable :). (I quite like how Inkscape shows common actions and key modifiers in the status bar, depending on your current mode/tool, so maybe something similar could work for Atlas). (Right-click in AoM appears to select the texture under the mouse for future drawing, which I guess is also a useful feature - maybe Atlas should have some way to do that too...)

Link to post
Share on other sites
  • 11 months later...

Hmm, I had a look at this again (inspired by AoK terrain discussions elsewhere), and tried doing a quick prototype in JS. I found something that seems to fix the terrain-blending glitches - I'm not sure it's perfect but I just want to write it down before I forget:

In the current implementation, for each tile, we look at the 8 surrounding tiles to find ones that are a different texture and a higher priority (i.e. that will be blended into this tile). For each distinct texture used by those higher-priority neighbours, we find all the neighbours using that texture and assume they're all part of the same splat and pick the appropriate blend shape. That is, we treat tiles as equivalent (for the purposes of splatting) if they share a texture, regardless of priority.

What works better: For each tile, consider the texture+priority of itself plus the 8 neighbours. Two tiles (t1, p1) and (t2, p2) are equivalent if t1 = t2 and there is no other tile (t3, p3) such that t3 != t1 and (p1, t1) <= (p3, t3) <= (p2, t2) (using a lexicographic order). That means splatting won't violate priorities - two tiles won't be in the same splat if there's an adjacent differently-textured tile between them in the priority order. Then for each equivalence class of higher priority than the current tile, we find all the neighbours in that class and pick the blend shape as before.

(Then we need to reconstruct large splats from all these individual tile blends (for polygon batching) without violating any orderings, but that doesn't sound too tricky - we have a partial order over tile-blends so we just do a topological sort to get a total order and try to arrange it so tile-blends with the same texture will be adjacent (is there an optimal algorithm for that?), and batch adjacent same-texture blends.)

Incidentally, our blend textures are a bit broken, e.g. blendtwoedges.dds and blendlshapecorner.dds don't line up properly with each other, so it'll never look right until we fix those.

Also incidentally, I guess it'd be nice to support multiple blend texture sets, e.g. roads will probably want a much sharper transition than sand. That's easy if the blend texture is solely dependent on the higher-priority texture being blended (not based on the pair of textures involved in the blending - sand over road will be the same as sand over grass etc) so we should probably do that at some point.

Link to post
Share on other sites

Quick prototype is here (should at least work in Firefox 3.6 and Opera 11). The first image is the input data (each tile has a texture (colour) plus priority). The second is what the current engine code implements, with obvious blending bugs. (The tiny coloured squares in a tile represent the neighbours that are blended into this tile). The third is my new approach to fix those bugs. The smaller images after it are the blending layers that will be drawn on top of each other. (In the current engine there's one blending layer per texture; in the new one there might be more.)

(The code in this prototype is disgusting and inefficient - it should be cleaner when done properly in C++.)

we just do a topological sort to get a total order and try to arrange it so tile-blends with the same texture will be adjacent (is there an optimal algorithm for that?)
Hmm, I'm becoming more doubtful there is one.

The problem is: Tile 1 blends an R texture on top of G (on top of the base texture B ), so say G1 < R1. Tile 2 blends G over R over G, so G2 < R2 < G2'. Tile 3 has R3 < G3. We want a total order that respects those per-tile orders, so it could be:

[G1, R1, G2, R2, G2', R3, G3]

or

[G1, G2, R1, R2, R3, G2', G3]

or

[R3, G1, G2, G3, R1, R2, G2']

etc. We want to minimise the number of times we switch texture when rendering in this order, so the first is very bad (we switch G->R->G->R->G->R->G) and the second is best (we switch G->R->G) and third is a bit worse (R->G->R->G).

It's easy to make an algorithm produce either the second or third orders: Pick a blend off the bottom of a random per-tile stack (say G1), then continue picking off blends of the same texture from any stack (in this case G2), until we run out of blends of that texture, then pick another random stack (say R1) and continue until finished. But if you make an unlucky random choice (say R3 first) you'll get sub-optimal behaviour. (The demo page demonstrates this - the 3rd layer could be merged into the 5th.)

I guess there are some heuristics that would improve matters (prefer to pick from the largest tile-stack, perhaps?) but I don't see a perfect solution. But hopefully perfection doesn't really matter in practice.

Link to post
Share on other sites

Committed some code now. See e.g. old system, particularly the bit on the right which mixes high-priority and low-priority white tiles and looks a mess, vs new system which handles that much more smoothly - I believe it should always behave reliably now (though please point out any counterexamples :)).

The remaining ugliness seems to be down to the blend textures, so I made some new ones (based on some old ones by CheeZy - I took the corner and edge blends, fixed the edge one to tile better, then rotated and combined them to produce all the other combinations, then tweaked some of the combinations by hand so it's better at diagonal lines).

Link to post
Share on other sites

Played around a bit in Atlas, and I'm not sure what to think of the new blends... Or really, they do seem a bit sharper than the previous ones which makes them less suited for textures which are really different from one another (which one rarely should do in either case). Otherwise they're great. And it's wonderful not having to see the bug turn up all over the place. It's far too easy to reproduce the bug in Alpha 3 so comparing the two is really showing why this is good improvement, nice work Philip :) Definitely worth to be listed among the prominent bug fixes for the next release.

Link to post
Share on other sites

My skills are mostly limited to randomly applying the clone brush and dodge/burn tool, so I wouldn't really use the term "artist" :D. Sharper blends seem okay for things like roads which are usually high contrast against the background, whereas natural terrain usually has much softer contrasts, but there's some terrain where it's probably not great. Needs art input, probably :). (It should be straightforward to test new blends - look in art/textures/terrain/alphamaps/standard/, change the corner and edge images to whatever you want (making sure they tile and mirror correctly), then combine them to form all the other images and edit as desired. The engine should hotload changes to the blend textures, in theory.)

Link to post
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

×
×
  • Create New...