为什么SetPixel无法正常使用ColorDialog?

时间:2014-05-10 18:48:25

标签: c# drawing

我尝试使用Bitmap.SetPixel方法更改图像颜色。我这样使用它时遇到问题:

Bitmap bmp = new Bitmap(Project1.Properties.Resources.gray_square_button);
int Width = bmp.Width;
int Height = bmp.Height;
Bitmap Nbmp = new Bitmap(bmp);
ColorDialog ColorDialog = new ColorDialog();
ColorDialog.AllowFullOpen = true;
DialogResult result = ColorDialog.ShowDialog();

if (result == DialogResult.OK)
{
    for (int y = 0; y < Height; y++)
    {
        for (int x = 0; x < Width; x++)
        {
            System.Drawing.Color BackColor = ColorDialog.Color;
            System.Drawing.Color p = bmp.GetPixel(x, y);
            int a = BackColor.A;
            int r = BackColor.R;
            int g = BackColor.G;
            int b = BackColor.B;

            Nbmp.SetPixel(x, y, System.Drawing.Color.FromArgb(a, r, g, b));
        }
    }
    PictureBox1.Image = Nbmp;
}

它只会在此图像中绘制一个我选择的颜色的正方形:

Note that the image won't show, only the color.

但是,如果我这样使用它,使用手动颜色和原始图像颜色引用(p BackColor的{​​{1}},这是ColorDialog定义的颜色):

if (result == DialogResult.OK)
{
    for (int y = 0; y < Height; y++)
    {
        for (int x = 0; x < Width; x++)
        {
            System.Drawing.Color BackColor = ColorDialog.Color;
            System.Drawing.Color p = bmp.GetPixel(x, y);
            int a = p.A;
            int r = p.R;
            int g = p.G;
            int b = p.B;

            Nbmp.SetPixel(x, y, System.Drawing.Color.FromArgb(a, r, 0, 0));
        }
    }
    PictureBox1.Image = Nbmp;
}

正确应用颜色并且图像也正确显示:

Here the color and the image displays correctly.

我尝试过的只是改变RGB颜色的1个值。但是,如果您选择一种颜色,颜色将不是您选择的颜色,而是根据颜色对话框颜色修改的颜色不同颜色。

int a = p.A;
int r = BackColor.R;
int g = p.G;
int b = p.B;

为什么ColorDialog RGB值不允许图像正确显示但只有彩色方块?

这是原始图片:

Original Image

1 个答案:

答案 0 :(得分:2)

您正在使用ColorDialog中的平面选定颜色替换“阴影”图像的颜色。所以基本上,你用对话框中的单个ARGB替换每个像素,无论ARGB如何,因此完全覆盖任何现有的图像信息。您也可以根据旧图像的尺寸从头开始绘制图像,而不必担心原始图像,因为它已被完全重写。

听起来你可能打算做的就是两种颜色混合在一起(原始图像+新颜色)。实际上有数百种方法可以做到这一点。我想到的是创建一个50%透明度的叠加层并将其应用于原始图像。您还可以将ARGB设置为平均值:

int a = (BackColor.A + p.A) / 2;
int r = (BackColor.R + p.R) / 2;
int g = (BackColor.G + p.G) / 2;
int b = (BackColor.B + p.B) / 2;

这将让您了解如何在更换原始颜色时考虑原始颜色,而不是更换它们。