Show Posts

This section allows you to view all posts made by this member. Note that you can only see posts made in areas you currently have access to.

Messages - Sergey Danchenko

Pages: [1] 2 3 ... 10
Any updates on this? It's really unfortunate to still not have an option to export from SP to glTF including tangents.

Normal map baked in SP produces visible seams all over the place in glTF viewers if no MikkT tangents are present on the mesh. I'm forced to use Blender and export from there to have high-quality glTF content without obvious shortcomings. Would be awesome to publish from SP directly to glTF and USDZ, considering that the vast majority of the content gets textured in SP.

That's great, thank you!


I wonder if there is a way to enable/implement DirectX raytracing in bakers for Pascal GPUs? Microsoft told about DXR that there would be some kind of a fallback layer for GPUs that don't have a dedicated raytracing hardware to utilize raytracing features. I guess this is the one:

Considering that RTX graphics card are too expensive, I believe that Pascal GPUs like 1080 Ti, 1080 and 1070 would be around and relevant for a couple of years at least. Yes, raytracing on those would be much slower than on RTX, but Pascal is still quite capable GPU and probably it would accelerate things substantially (even baking AO from Mesh 2x times faster would be quite nice  ;)).

Any chance to explore that possibility? Thanks!

That was a great idea! Seems like it will support tiling, after all :)

Gradients are generated from pixel position in a map (UV coordinates), while random luminance mask controls gradient rotation matrix. Because of random luminance mask, the actual value that rotates the gradient is kept the same for each individual island in a mask — it's a corner stone in this implementation. So, as pixel position changes, so does the gradient value, but overall direction for a given island is preserved.

At first, I've tried to use Transform node to downscale the map, so islands located at the edges would move inside the map and gradient will be applied to them without wrapping around. Transform node scaled down at 50% and set as "Input +1" for resolution would allow to do this without resampling pixels, so no information will be lost. Then apply the gradient and use Transform node again with 200% scaling and Input -1 resolution to get back to original resolution. Unfortunately, this would limit the node tiling to 4k resolution, as you can't get over 8k in SD yet.

Then I've realized that indeed, with very long islands in the map, scaling down at 50% won't be enough. To make tiling work it should be scaled one more time, to 25%, and then vice versa. That would effectively limit the node to 2k resolution only, which is unacceptable.

I've decided to follow your great idea and leveraged Randomize Mask node to mark islands that are located at the edges of the map and in the corner, then flood fill those islands to make a map for them. Then I've figured that I can modify gradient function to warp around marked islands as necessary, so no actual map offset would be necessary (instead the gradient will offset). Also it became apparent that I don't need to mask islands that are located on both sides of the mask — just pick one side and make sure the gradient wraps correctly to the other side.

So, with wrapping islands masked, I've used them to put some additional parameters in gradient function. Islands marked as located at the left border of the map will get horizontal U offset of 1 unit, so the gradient would warp there exactly by one texture tile. Same for islands located at the top - mask them and offset gradient vertically on V by 1 unit. For corner island that touches both left and top borders of the map, offset both U and V by 1. Voila! — seamless gradient.

Now I have something like this almost ready (first image below): node that allows to apply random and variable direction gradient to individual islands in a mask, with support for donut-like shapes, adjustable and variable range for gradient, global gradient angle control and a pretty invert (!) button. :P

I wonder if there any use for an additional node that will mark islands that will wrap when the map will tile (second image below)? I have a feeling that it may come useful, but can't right away tell in which way. The map can be neatly packed in a RGBA with horizontally wrapping islands in R, vertically - in G, corner islands in B and general mask for all of them in A.

 :-\ Looks like my gradient node won't support tiling for now. It does work with donut-like shapes, but I can't figure out how to make the gradient to wrap correctly on islands that located on both sides of the mask (i.e. that need to tile). Can't have everything at the same time, eh?..  ;D

The most unfortunate thing is that I'm pretty confident it can be done, but at this time I'm lacking a required math background to make it happen.

No, I've stopped working on it since Flood Fill was released. The node is functional, but requires some love on the organizational side. Judging from this topic, it looks like the node still may be useful for some cases where Flood Fill can't operate properly. I'll look into finishing and releasing it.  ::)

I guess my Randomize Mask node implements something close to a Flood Fill algorithm as in the OP. It's a brute force approach with some optimizations, but it's quick enough to be usable on practice. As a benefit, it can tackle almost any shape given enough iterations  ;D.

It was designed to fill an array of islands with random luminance values (but keep this value the same inside a given island) to create a random luminance mask from/for bitmap images.

On images attached below you can see how the node will spread values across shapes in iterations, with the end result in the last frame.

Some time later I've found that a random angle gradient can be applied to such shapes using additional processing (see last image).

The node mentioned above is released and thoroughly commented, so anyone interested can take a peek inside.  ::)

By the way, Eggfruit, you've pretty much described how Randomize Mask node come together. It's a bunch of Pixel Processor nodes with something like "ray casting" functionality. Each Pixel Processor samples a number of pixels (I've stopped at up to 8 px per iteration) to the left/right/top/bottom from current coordinate and stops if it finds a black one (i.e. island border). Then it assumes min or max sampled value as a value for a processed pixel. In this way, min/max pixels can be spread throughout the islands without crossing the island's borders. To optimize it, you indeed can reduce resolution at which computations are being made, and it will drastically affect performance in a good way.

Some links:,5158.0.html,16547.0.html


This is my entry for the contest :).

I was looking for something special and something that will harness the power of Iray and MDL. Decided to go with an optical fiber self-illuminated cloth material. It is a material made from specially fabricated optical fiber wires. Regularly, the light shouldn't leak from optical fiber, but for this material a large number of laser cuts are being made on the fiber, so the light would leak out along the length of a wire producing beautiful light sparkles and streaks.

The material is made as a MDL driven by Substance graph. Images were rendered using IRay with displacement mapping. As it's basically all glass, there's A LOT of refraction on this material, so it was a challenge on itself to render it out.  ;D

On Artstation:

Cool! Can't wait to check it out  ;D

thephobos, I haven't shared anything yet. I was going to make a push and finish the node, but it seems that it may be too late  ;).

You're welcome and good luck!  ;)

I've meant areas like on the first picture attached - it's really the same issue with missing projection rays that you've (mostly) fixed already. Unfortunately, on shapes like this, it's close to impossible to bake a normal map without any artifacts - at most, by moving around the geometry you can choose to have them either on top or on the side.  :D

That's why you should change the geometry to have a better bake. Consider adding a slight bevel on top of your low-poly shape (see the second picture attached for an example). Generally, you should avoid right angles (close to 90 degrees) on your shapes as much as possible, because it's pretty hard to bake them without artifacts. It's a good practice to slightly exaggerate such angles and make them a bit more round and smoother than they are on real objects - you will not only get a better normal map from it, but the object also will catch highlights on those edges better and keep visual integrity on larger distances.

That said, you have really sharp edges on top of your high-poly — it may be realistic, but will not play so well for the normal map. Try to make them much more round and smoother - you can follow the profile on the low-poly mesh with bevel you'll be adding to it.

Lastly, there are some redundant edges on the top side of the low-poly (see the third picture attached). They can affect baking in a negative way, so remove them (and check UV's after that).

With those three steps, you should get a much better normal map.

Now, your issue is that your low-poly mesh doesn't follow the shape of the high-poly mesh close enough. It's a very similar artifact (basically the same) that you would be getting baking a high-poly cylinder shape into a low-poly with not enough geometry. Check out this thread, it has some great insights on this:

Basically, to fix this, you should add some geometry to your low-poly where there are artifacts you're seeing in the normal map. Also, make sure that your low-poly wraps high-poly as close as possible - there are a few areas on top where that isn't the case, and you get some thin line-like artifacts on your normal map because of this.

And finally here's a quick mockup of what's going on with your bike. Blue is low-poly, red is high-poly. Blue line is the distance between the low-poly and the cage (a "push" for the cage or Frontal Distance if you don't use a cage in SP) and an approximation of a pixel for which a particular baking ray will be cast. The black line is a ray cast for a particular point on the side of your mesh (where you see the artifacts). As you can see, the ray cast from the side of the low-poly will hit the top side of the high-poly (black dot). Normals baked from such will produce visible artifact on you normal map because it will contain normals from the top of the mesh on the side of the mesh. Additional geometry should alleviate that.

You have broken smoothing groups (soft/hard edges) on your low-poly mesh in SP. Everything is soft. Hence the weird smoothing on top of the mesh that can be seen even without any maps/materials applied. Normal map you've been baking struggles to compensate for that, thus artifacts are present.

The mesh should look more like on the right side of the picture below. Try to re-export your meshes from your 3D app and check if Smoothing Groups export is enabled. Also, you can try to export in FBX format if OBJ won't do for some reason. And don't forget that for every hard edge in your LP mesh you should have a split in your UV's for normal map to be baked seamlessly. Most likely you would need to slightly alter your UV's for this mesh to account for that.

Good luck!  :)

I support the request to put this feature back. Substance Designer is for crazy things, and you can't really foretell what bake configuration would be necessary. Being able to override settings for each bake separately was a huge boon.  ::)

Nice catch! Thank you. Fixed and re-uploaded  :).

If you can recommend something, i will really appreciate that.

Vincent Gault's YouTube channel has some informative videos on Pixel Processor: Apart from that, there's not so much content around, unfortunately.

In general, I would say that most important things for getting familiar with Pixel Processor are the following:

1) Pixel Processor executes its functions on a per-pixel basis and in parallel. It means that for every pixel in the map, the same function will be executed. You can't get the result of such processing to influence something that happens inside the same Pixel Processor node. You can, however, process your maps in several steps by chaining some Pixel Processor nodes in a succession. Intermediate nodes can act as data storage/provider for next nodes in the chain.

2) It's all about manipulating pixels' luminance values. For each individual pixel in a map, you can sample (pick luminance value) basically any pixel on the same map or in an another map plugged to the same Pixel Processor. Alternatively, you can right away write some new values to the pixels without sampling anything based on some logic implemented through the functions.

3) To manipulate values, you'll need to assemble some functions inside Pixel Processor. One needs a very basic understanding of programming and math to grasp it. You'll need to have some idea of what is Float, Integer and Boolean, how If-Else conditions work, what are some other function nodes available inside Pixel Processor. Then it's math - take some value, multiply it with another, add something to it, subtract, etc. The math here CAN be pretty advanced, but it does not necessarily have to be like that. You can use what you know and still get nice results.

4) Actually making some simple Pixel Processor functions helps a lot when you want to quickly get familiar with it. Then you can try new and more complex ideas, make some simple filters using the Pixel Processor, etc. This will get things rolling and in no time, you'll find yourself assembling sophisticated functions to make it do what you want. ;D

Pages: [1] 2 3 ... 10