troubleshooting Question

VB.NET - Make Bitmap Grayscale (Bitmap.SetPixel??)

Avatar of HATCHET
HATCHET asked on
.NET Programming
6 Comments1 Solution2381 ViewsLast Modified:
I'm trying to take a System.Drawing.Bitmap object in VB.NET and make it grayscale.

1) Can anyone please give me an easier, more efficient way of making an image grayscale?  I'm an expert in VB 5 and 6 and doing this is EASY and fast in VB5/6, but I'm just getting into VB.NET and it's very confusing how you're supposed to do things.  It's irritating how Microsoft keeps you away from any real useful functionality that they deem "low-level".  It seems they want to keep you at a high level with all the objects, etc... but the objects don't do everything I want, and their use is often cryptic.

2) I tried to do a pixel by pixel color conversion like this... but the following line of code causes the error "An unhandled exception of type 'System.ArgumentException' occurred in system.drawing.dll.  Additional information: Invalid parameter used.":

objBITMAP.SetPixel(intCounterX, intCounterY, clrNew)

What's wrong with my code?  It seems straight forward.


Private Sub mnuEffectsGrayscale_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles mnuEffectsGrayscale.Click
   Dim objBITMAP   As System.Drawing.Bitmap
   Dim intCounterX As Integer
   Dim intCounterY As Integer
   Dim clrCurrent  As System.Drawing.Color = New System.Drawing.Color()
   Dim clrNew      As System.Drawing.Color = New System.Drawing.Color()
   Dim intCurrent  As Integer
   Dim intNew      As Integer
   If picDisplay.Image Is Nothing Then Exit Sub
   objBITMAP = picDisplay.Image.Clone
   For intCounterY = 0 To objBITMAP.Height - 1
      For intCounterX = 0 To objBITMAP.Width - 1
         clrCurrent = objBITMAP.GetPixel(intCounterX, intCounterY)
         intCurrent = RGB(clrCurrent.R, clrCurrent.G, clrCurrent.B)
         intNew = 0.33 * (intCurrent Mod 256) + _
                  0.59 * ((intCurrent \ 256) Mod 256) + _
                  0.11 * ((intCurrent \ 65536) Mod 256)
         If intNew < 0 Then intNew = 0
         If intNew > 255 Then intNew = 255
         clrNew.FromArgb(intNew, intNew, intNew)
         objBITMAP.SetPixel(intCounterX, intCounterY, clrNew)
      Next intCounterX
   Next intCounterY
   picDisplay.Image = objBITMAP
End Sub

Our community of experts have been thoroughly vetted for their expertise and industry experience.

Join our community to see this answer!
Unlock 1 Answer and 6 Comments.
Start Free Trial
Learn from the best

Network and collaborate with thousands of CTOs, CISOs, and IT Pros rooting for you and your success.

Andrew Hancock - VMware vExpert
See if this solution works for you by signing up for a 7 day free trial.
Unlock 1 Answer and 6 Comments.
Try for 7 days

”The time we save is the biggest benefit of E-E to our team. What could take multiple guys 2 hours or more each to find is accessed in around 15 minutes on Experts Exchange.

-Mike Kapnisakis, Warner Bros