I know that this won't directly invert a colour, it will just 'oppose' it. I was wondering if anyone knew a simple way (a few lines of code) to invert a colour from any given colour?
At the moment I have this (which isn't exactly the definition of an invert, because if I pass it a grey / gray colour it will return something extremely similar e.g. 127, 127, 127):
const int RGBMAX = 255;
Color InvertMeAColour(Color ColourToInvert)
{
return Color.FromArgb(RGBMAX - ColourToInvert.R,
RGBMAX - ColourToInvert.G, RGBMAX - ColourToInvert.B);
}
It depends on what do you mean by "inverting" a color
Your code provides a "negative" color.
Are you looking for transform red in cyan, green in purple, blue in yellow (and so on) ? If so, you need to convert your RGB color in HSV mode (you will find here to make the transformation).
Then you just need to invert the Hue value (change Hue
by 360-Hue
) and convert back to RGB mode.
EDIT: as Alex Semeniuk has mentioned, changing Hue
by (Hue + 180) % 360
is a better solution (it does not invert the Hue, but find the opposite color on the color circle)
You can use :
MyColor=Color.FromArgb(MyColor.ToArgb()^0xffffff);
It will invert MyColor.
Try this:
uint InvertColor(uint rgbaColor)
{
return 0xFFFFFF00u ^ rgbaColor; // Assumes alpha is in the rightmost byte, change as needed
}
Invert the bits of each component separately:
Color InvertMeAColour(Color ColourToInvert)
{
return Color.FromArgb((byte)~ColourToInvert.R, (byte)~ColourToInvert.G, (byte)~ColourToInvert.B);
}
EDIT: The ~ operator does not work with bytes automatically, cast is needed.
What you already have is an RGB-Invert. There are other ways to classify colors and hence other definitions for the Inverse of a Color.
But it sounds like maybe you want a contrasting Color, and there isn't a simple Inversion that is going to work for all colors including RGB(127, 127, 127).
What you need is 1) a conversion to HSV (see ThibThibs answer) and invert the Hue, but also 2) check if the Hue isn't to close to the middle and if so go to either fully bright or fully dark.
If you want to change every color, try a rotational function (shifting or adding) rather than a flipping function (inverting). In other words, consider the range of 0 to 255 for each single color (red, green, and blue) to be wrapped, connected at the tips like a circle of values. Then shift each color around the cirle by adding some value and doing mod 256. For example, if your starting value for red is 255, and you add 1, you get 0. If you shift all three colors by 128, you get dramatically different values for every original color in the picture, even the grays. Gray 127, 127, 127 becomes white 255, 255, 255. Gray 128, 128, 128 becomes black 0, 0, 0. There's a photographic effect like that called Solarization, discovered by accident by Man Ray in the 1930's.
You can also do rotational operations on each color (red, green, blue) by a different amount to really mess up a picture.
You can also do rotational operations on hue, shifting the hue of every original color by some amount on the hue circle, which alters all the colors without altering the brightness, so the shadows still look like shadows, making people look like Simpsons or Smurphs for example.
The code for a shift by 128 could look like:
public static Color Invert(this Color c) => Color.FromArgb(c.R.Invert(), c.G.Invert(), c.B.Invert());
public static byte Invert(this byte b) {
unchecked {
return (byte)(b + 128);
}
}
The most simple and lazy way I made it to work with having not only triple 12x, but mixed values, is this:
Color invertedColor= Color.FromArgb(fromColor.ToArgb() ^ 0xffffff);
if (invertedColor.R > 110 && invertedColor.R < 150 &&
invertedColor.G > 110 && invertedColor.G < 150 &&
invertedColor.B > 110 && invertedColor.B < 150)
{
int avg = (invertedColor.R + invertedColor.G + invertedColor.B) / 3;
avg = avg > 128 ? 200 : 60;
invertedColor= Color.FromArgb(avg, avg, avg);
}
Now, invertedColor
has a different color that the original, even if we have a 128, 128, 128 or close to it color value.
I've created this simple function for VB.NET:
Public Shared Function Invert(ByVal Culoare As Color) As Color
Return Color.FromArgb(Culoare.ToArgb() Xor &HFFFFFF)
End Function
And this one for C#:
public static Color Invert(Color Culoare)
{
return Color.FromArgb(Culoare.ToArgb() ^ 0xFFFFFF);
}
来源:https://stackoverflow.com/questions/1165107/how-do-i-invert-a-colour