Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How do you edit a .png programmatically?

Tags:

c#

png

I have 28 images that have 3 sizes each (84 total) that are all monochrome with different alpha layers to make each image. I want to make each of them available in 5 different colors. that would be 420 images total. This would obviously be a huge pain to do manually. I do not have Photoshop so any type of photoshop function is not a valid answer. I have Paint.NET but the adjust hue doesn't work for me because changing the hue alone does not give me the colors I want.

Basically what I need to do is for every pixel in the image, take the RGBA value and replace the RGB with a new RGB value and keep the same A value.

Anyone know how to do this? I had no luck searching on StackOverflow or Google (probably using the wrong search terms).

I would prefer an answer in C# or VB.NET but if anyone knows how to do this in any language maybe I can apply it to C# or VB.NET.

--Edit--

In case anyone finds this and is looking for the answer, here's what I got based on the link from Yorye Nathan.

private const int RED = 51;
private const int GREEN = 181;
private const int BLUE = 229;

private const int NEW_RED = 170;
private const int NEW_GREEN = 102;
private const int NEW_BLUE = 204;

private void Form1_Load(object sender, EventArgs e)
{
  if (openFileDialog1.ShowDialog() == System.Windows.Forms.DialogResult.OK)
  {

    Image OriginalImage = Image.FromFile(openFileDialog1.FileName);
    Image NewImage = ColorFilter(OriginalImage);

    pictureBox1.Image = OriginalImage;
    pictureBox2.Image = NewImage;
  }

}

public static Image ColorFilter(Image originalImage)
{
  Bitmap newImage = new Bitmap(originalImage);
  BitmapData originalData = (originalImage as Bitmap).LockBits(new Rectangle(0, 0, originalImage.Width, originalImage.Height), System.Drawing.Imaging.ImageLockMode.ReadWrite, System.Drawing.Imaging.PixelFormat.Format32bppArgb);

  BitmapData newData = (newImage as Bitmap).LockBits(new Rectangle(0, 0, originalImage.Width, originalImage.Height), ImageLockMode.ReadWrite, PixelFormat.Format32bppArgb);

  int originalStride = originalData.Stride;
  System.IntPtr originalScan0 = originalData.Scan0;

  int newStride = newData.Stride;
  System.IntPtr newScan0 = newData.Scan0;

  unsafe
  {
    byte* pOriginal = (byte*)(void*)originalScan0;
    byte* pNew = (byte*)(void*)newScan0;

    int nOffset = originalStride - originalImage.Width * 4;

    byte red, green, blue;

    for (int y = 0; y < originalImage.Height; ++y)
    {
      for (int x = 0; x < originalImage.Width; ++x)
      {
        blue = pOriginal[0];
        green = pOriginal[1];
        red = pOriginal[2];

        if (pOriginal[0] == BLUE && pOriginal[1] == GREEN && pOriginal[2] == RED)
        {
          pNew[0] = (byte)NEW_BLUE;
          pNew[1] = (byte)NEW_GREEN;
          pNew[2] = (byte)NEW_RED;
        }

        pOriginal += 4;
        pNew += 4;
      }
      pOriginal += nOffset;
      pNew += nOffset;
    }
  }
  (originalImage as Bitmap).UnlockBits(originalData);
  (newImage as Bitmap).UnlockBits(newData);
  return newImage;
}
like image 347
Nick Avatar asked Mar 26 '12 01:03

Nick


1 Answers

Check this question out. Tweak a little with the pixel's bits replacement to make it add them instead of replacing them, and you're good to go.

like image 183
SimpleVar Avatar answered Oct 09 '22 00:10

SimpleVar