views:

240

answers:

4

How can I do this?

int blue = Color.Blue.ToArgb();
int yellow = Color.Yellow.ToArgb();

blue = (blue + yellow) / 2;

Color Blue = ConvertFromRGB(blue);
+8  A: 

I think what you're looking for is this:

var blueColor = Color.FromArgb((blue + yellow) / 2);

However, I don't think it will give you the result you actually want.

You must be quite careful about mixing colours in this way. The int value representing a colour in ARGB form is fairly arbitrary as far as the coder is concerned. It's probably best to mix RGB components individually, like:

var color1 = Color.Blue;
var color2 = Color.Yellow;
var blueColor = Color.FromArgb((color1.R + color2.R) / 2,
    (color1.G + color2.G) / 2, (color1.B + color2.B) / 2);

This interpolates (taking the centre point) between two colours, and should give you something that looks much more like the blend of the two colours.

(Note that I assume you're referring to the System.Drawing.Color type here.)

Noldorin
+1 for clear explanation on color blending
Jason Heine
Cheers. :) And yeah, you have admittedly answered the (direct) question, though it's important that the OP is aware of what it actually does, as you seem to realise.
Noldorin
+3  A: 

I think this is what you might be looking for:

int blue = Color.Blue.ToArgb();
int yellow = Color.Yellow.ToArgb();

blue = (blue + yellow)/2;

Color Blue = Color.FromArgb(blue);
Jason Heine
I really don't think this is going to give the right result, though it may be what the OP is wanting. This is generally *not* the right way to blend colours. (Also, how did the votes of this answer rocket it up when mine was originally equivalent and first?)
Noldorin
This will in fact do something, but it will not average the color components in every case.
PeterAllenWebb
I just answered what it appeared they were looking for. There is nothing in the question asking about blending.
Jason Heine
Given that we're already doing enough guess-work to answer this question, I don't think it's a large step futher to presume that he wants to blend colours. I can't in any way see a useful for interpolating with the single ARGB value.
Noldorin
You are right, we are just guessing. I agree, there is really no point in getting a Color with a single ARGB value. I will say that I do like your answer which gives a clear explanation on proper blending of Colors, which is what they are probably trying to do.
Jason Heine
+1  A: 

Just average the colors component-wise, if that is what you are trying to do:

Color average = ConvertFromRGB((Color.Blue.R + Color.Yellow.R) / 2), (Color.Blue.G + Color.Yellow.G) / 2), (Color.Blue.B + Color.Yellow.B) / 2));
PeterAllenWebb
Yes, exactly. This is the correct way to mix colours, as I've pointed out in my post. Note: I think you mean to use `Color.FromArgb` instead of `ConvertFromRGB`.
Noldorin
A: 

It would be useful to know what you're expecting from the second assign to 'blue' - you certainly won't be getting a shade of blue (more like red).

The problem is that the Color class keeps its ARGB values as Int32 because each of the 4 bytes represents one of the Alpha, Red, Blue and Green values.

Asking to add together two colours in their Int32 form is going to cause unexpected values, as one byte 'overflows' into the next (what happens when you add 255 and 1?)

Color.Blue, for example, is -16776961. That's because it has 4 bytes that look like this:

0: 255
1: 0
2: 0
3: 255

Or:

11111111 00000000 00000000 11111111

You'll find it much clearer to break the ARGB components down into individual bytes, System.Drawing.Color allows you to do this via its instance properties:

blue.A
blue.R
blue.G
blue.B

You can safely manipulate these, but remember that they're an instance of Byte, so you can't assign a value out of the range 0-255. To create a colour from the component bytes, use:

Color.FromArgb(a, r, g, b);

Where a, r, g, b are bytes.

Somewhat confusingly, Color.FromArgb accepts int parameters, rather than bytes. I'm afraid I've no idea why, someone better than me will have to answer that, but casting a byte to an int with produce an int with a value between 0 and 255, so it's safe to use this. Color also has a private CheckByte class that it passes each argument into so you'll get an ArgumentException rather than an unexpected color (that you'll likely get with your non-component approach).

Matthew Brindley