# Selectively mix shaders based on color input

This might be a bit confusing, so my apologies before hand. I'm making a shader/nodegroup that emulates colors under a blacklight. For most colors (greens, reds, blues), it works just fine and looks perfect, but for others (whites and yellows) the result isn't what's expected.

What I'd like to do, is be able to have the shader recognize that the color input is white, yellow or any of the other colors that don't work right, and be able to isolate them so I can correct them with the proper nodes. But I'd also like to have it know when I'm using the colors that do work, and not apply the corrections. So basically, selectively apply corrections based on the input color.

I imagine the solution is probably some logic type stuff using math nodes and maybe the separate RGB nodes and such, but honestly that is beyond me. It's obviously possible to just use 2 separate groups or inputs for them, but I'd ideally like to be able to plug in image textures and such and have it "just work".

Any help would be much appreciated.

• can that help? blender.stackexchange.com/questions/148887/… – lemon Oct 15 '19 at 7:16
• Not interested in that. I'm more interested in the punchy blacklight colors. That solution doesn't work for that. I'm quite happy with my solution as it definitely has the punchy colors and looks right, I'm just mainly focused on fixing the specific colors that I'm having problems with. Not another blacklight solution. – AxiomDes Oct 15 '19 at 7:44
• You should be more accurate about what you obtain so far and what (and why) it does not work for some colors. If not you may have answers that just indicate "use separate rgb to compare the colors". – lemon Oct 15 '19 at 7:52
• I figured it was pretty clear what I wanted. I just want to be able to take a color input of whatever, and if it's one of the chosen colors (in this case, yellow or white), be able to manipulate it while leaving the others alone. Why I need to do it is irrelevant to the question really. – AxiomDes Oct 15 '19 at 8:04

## 1 Answer

To pick out similar colors in a spectrum, there has to be a notion of a distance between colors, which more or less makes sense to the eye. One (perhaps naive) way to do it would be just to take the 3D distance between colors in whichever space you are using for comparison. If that's RGB, that would be sqrt(dR*dR + dG*dG + dB*dB). You could put this in a node group:

Starting with the colors in the top left, supposing for the black light effect we generally just saturate the colors a bit. (top right).

Then we can use the RGB-Distance node group to pick out colors similar to examples we've picked.

The bottom left square above shows the output of the top Color Ramp node in the tree below. It's a mask of colors which are quite-like-white in the original (top left) square.

Masks like that can be used as factors to mix between the saturated tiles and the ones we've picked out for special treatment. The top branch picks out whites, and replaces them with a darker blue, and the bottom branch replaces yellowish squares with magenta.

This might do it for you on its own.. but it could be tweaked to place more emphasis on hue, brightness, etc., by changing the definition of distance between colors.

I should point out that to keep things linear, and let me E use an eyedropper to pick colors from the screen, I've set the color-management in the .blend to Raw, with no sRGB in the display. You will probably want to change that.

• Works perfectly. I had tried another solution that I had found searching around, but it was hard to really "pick" the colors without a bunch of work. This is one neat and clean solution that's easy to tweak if I need to pic a range of colors. Thanks. – AxiomDes Oct 18 '19 at 6:27
• @AxiomDes Thanks. Just another quibble. To map the color distance to [0,1] for the color ramp, strictly, you would have to multiply the 'RGB Distance' output by 1/sqrt(3).. but since we're only using the lower end of the scale here, I thought it was OK not to. – Robin Betts Oct 18 '19 at 8:33