Deluanay Triangulation shaders?

Hi guys,

Does anyone know of any graphics effects or Shaders in corona that can produce low -poly style art ( Deluanay Triangulation) ? The closest one I could find was crystallize filter. But that is polygon crystals, not triangles. Is there any way to modify any of those?

Thanks. 

rakoonic ported a Voronoi-based technique here: shader Voronoi diagrams and Delaunay triangulation are dual to one another–the state of one describes the other, and vice versa, albeit in a different way–so it possibly fulfills what you’re after.

That said, the “low-poly” bit doesn’t seem strictly related. Do you have a particular use in mind here?

Hi StarCrunch

Thank you for your response. 

By low-poly i meant this type of art style, and they utilize deluanay triangulation in some sort or form to generate the style 

http://static.wixstatic.com/media/d069d3_3aa663fb7b9cca386f5582508e2ac99b.png/v1/fill/w_459,h_443,al_c,usm_0.66_1.00_0.01/d069d3_3aa663fb7b9cca386f5582508e2ac99b.png

Now in Github there are lot of JS libraries that can achieve this. But it seems nearly impossible to transfer those to pure Corona SDK lua. 

More specifically, 

I meant this type of use 

http://asifmallik.github.io/  put any image there and you can see what i meant. 

Honestly i think i could write a plugin module for that but it would probably take some time.

–SonicX278 

You probably wouldn’t gain much from doing the Delaunay triangulation in-shader (though I’d enjoy being proven wrong here), seeing as it’s really a big preprocessing step. Roland Yonaba (of Jumper fame) has some code for it (in Lua) here. There’s a decent chance you could simply use a bunch of polygons, the trouble being to come up with a decent point cloud to triangulate.

How difficult this might be would depend a lot on the quality you’re going for, which in turn depends on your access to the color information. If you don’t care so much about well-distributed colors you could just generate a reasonably fine jittered grid and then triangulate those points, using the color at each point in the original.

Otherwise, you’ll have to accumulate some info, and there indeed some shaders could come into play, for instance by doing a multi-pass reduction to plant the average RGB (and maybe a low-res x, y offset in the alpha channel) into some small rects that you could then sample, coalescing near-enough colors. Perhaps this same idea could also work well in tandem following a Sobel filter, though that’s probably a bit more work.

I ported some Worley noise code (e.g. see Drilian’s patterns here) if that might be useful.

Hi StarCrunch, yes currently I am trying to use the github Lua module by Yonaba to generate the triangles, with somewhat success. But then the question becomes how do I apply that trinagle (or mesh) field on an image? The low-poly art style usually implements ‘average blur’ on each of the trinagles. OR just gets the RGB value at the exact center of each triangle and fills the entire triangle with it. I assume RGB access isn’t something available yet in Corona? Using blur would also mean I would have to apply blur to  specific areas (triangle shaped) of the image ( like having a polygon layer on top of the image and apply blur so that it effects the image underneath I guess? ) many times. Is that possible ? The reason I was thinking shader is because Corona already has a built in shader called ‘Crystallize’ which is very similar to low-poly, except the Corona SDK one isn’t triangular ( pentagon). 

On a related note, Drilian’s Worley noise comes very close to what I would want to achieve, except in triangular shape and 

instead of the seemingly random (?) color fill, I would just have to use blur OR RGB fill from the image. But then it’s the same question again.

Sonic, that would be great :D 

this type of ‘low-poly’ art is the hottest new trend and any app including games could benefit from it. 

If someone doesn’t beat me to it I’ll give it a go! I have a couple clients and plugins/modules to finish up first though.

–SonicX278

I was going to start on this for another project I’m working on, but I’ll put that off since you’re working on it @Sonicx278. Looking forward to seeing what you produce!

Awesome! Well like i said i have a couple clients and plugins to finish up and then i can start. @Alex@Panc – If you do end up starting on it please post back here so I know if i should or not. Thanks!

–SonicX278 

@ farjadfarabi_czs  I’m curious how much success “somewhat” is.  :D If you have the proper boundary and simply need to fill in the interior colors, the rest will probably be fairly straightforward.

Crystallize might even be using Worley. I think Drilian’s version does use random colors, yes. Apart from the rough geometry of the noise algorithm you can impart quite a lot of variety to it. For reference, my ported code for it is included among the code I used during the Corona Geek shader shows, recent snapshot here. (Some bugfixes pending, just a bit lazy about updating.  :))

The color is a pain if you need to hoist it out from the GPU, e.g. with display.colorSample(), but easy enough on the shader. The blur version might be a bit more work (because you’d have to fight interpolation if you want to sample in the fragment shader; not an issue if your GPU allows it on the vertex side), but if you can pass the triangle’s centroid (or some other preferred center) in through the userdata you’ve got a lot of what you need.

@ SonicX278  If you’ve not already got a technique in mind, one idea might be to build on what I’ve just mentioned and render those colored triangles into a canvas, then re-create the image / sprite using that instead. (And allow this to be saved, so this could be done during development and transparent to the end user.)

Do you think just creating a whole bunch of polygons with three vertices would be easier?

–SonicX278 

For a still image, yes. For a sprite, not so sure… But don’t let that stop you!  :slight_smile:

AlexPanc, just curios, were you thinking to use this one a game?

I should mention that I am looking for this to use as a graphics effect on a puzzle game I am working on. I could just use the 10+ websites that do low-poly art and load the images as part of my app, but I am also adding the option so users can add their own photos and for that I need to be able to generate this within the app.

StarCrunch, display.colorSample(), I had no idea such a method existed. :open_mouth:

The lua delunay module has a method where it calculates the center of a triangle. 

And speaking of “somewhat”, right now I just split the Area into small squares and pass the corners of those squares as vertices and triangulate them. I know it’s not ‘random’, but the mesh generated looks okay enough for use. 

I think for a start i could do still images and then after polishing that up i could add sprite support.

–SonicX278 

Hey Sonic,

If you are talking about ‘low-poly’ effect as the phrase is generally used, I don’t think sprites will have much of a use for it. 

But you never know. :wink:

What i was thinking was starting off with one triangle ( Triangle has three points ) and the next triangle that’s spawned can “remember” two points from the first triangle and use that and randomize a third point and then it draws itself and then the third one and so on do the same thing. How does that sound?

Here’s an example in squares that @Alex@Panc wrote for me last year. We could start off in this direction. All you would need to do it get the math correct and your set.

local row = 35 local column = 20 local cellWidth = 15 local cellHeight = cellWidth local centerX = display.contentCenterX-cellWidth\*column/2-cellWidth/2 local centerY = display.contentCenterY-cellHeight\*row/2 -cellHeight/2 local cell = {} local function handleTile(self, event) if event.phase == "ended" then self:setFillColor(0,.5,.25) return true end end local function createGrid() for x = 1, row do cell[x] = {} for y = 1, column do cell[x][y] = display.newRect( x\*cellWidth, y\*cellHeight, cellWidth, cellHeight ) cell[x][y].strokeWidth = 0.6 cell[x][y]:setStrokeColor(1) cell[x][y]:setFillColor(0) cell[x][y].x = y \* cellWidth + centerX cell[x][y].y = x \* cellHeight + centerY cell[x][y].touch = handleTile cell[x][y]:addEventListener("touch", cell[x][y]) end end end createGrid()

–SonicX278 

@Alex@Panc any comments on this?

–SonicX278 

Just a note. Ill be out of town till Monday sadly. Ill get started right back when i get back!

–SonicX278 

@ SonicX278

That sort of technique wouldn’t have the characteristics of a Delaunay triangulation (which tends to enforce certain overall angle constraints, e.g. to eliminate slivers), but that seems to have been an example rather than a requirement, anyhow.

What you describe is something along the lines of a random walk.

This is fine (and touches on other useful applications as well), but you will need to be ready to deal with the new triangles penetrating old ones and be able to respond in some intelligent way, e.g. by rejecting your original candidate in that case and using the smaller one that would bridge the gap (which gets hairier if there’s no common vertex). To play on your earlier personification, this would also suggest your triangles should “forget” their sides, so that you could establish whether such a connection was even still viable.

That code will need some adjustments. The connectivity wouldn’t be like a rectangular grid, although triangles can still tile the plane. This is a good overview.

(I’ve been preparing some geometry articles for what feels like ages now, and though they probably still won’t land for a good while, I do go into a lot of this math. If and when the time comes I could supply code or excerpts.)