Results 1 to 7 of 7

Thread: Getting Average Color of Form BackgroundImage

  1. #1

    Thread Starter
    PowerPoster
    Join Date
    Feb 2016
    Location
    Tennessee
    Posts
    2,437

    Getting Average Color of Form BackgroundImage

    I was searching for this code today and thought I might share it. In my case, I have a clock on screen that I want to background color to blend in with the Background Image of a form. The ConvertTo24bpp sub wanted you to pass in an image, and I changed that to a bitmap.

    The GetAverageColor1 function uses 24bppRgb to make the code faster (as I read). But eventually I want to turn it into a memory stream for better performance and I will probably reduce the size of the bitmap before passing it as well.

    If you would like to see the whole post where I found the code, you can go here: https://social.msdn.microsoft.com/Fo...rum=vblanguage

    I included how I call the code and it's in the BackgroundImageChanged Event of the Form. Not much to it, but I like the effect. Hope maybe someone enjoys using or seeing the code.

    Code:
        Private Sub ListviewForm_BackgroundImageChanged(sender As Object, e As EventArgs) Handles Me.BackgroundImageChanged
            Dim NewBmp As Object = rk.GetValue("LastWallpaper")
            Dim bmp As Bitmap = New Bitmap(CStr(NewBmp))
            bmp = ConvertTo24bpp(bmp)
            Dim clr As Color = GetAverageColor1(bmp)
            LittleTime.BackColor = clr
            rk.SetValue("ClockAutoBackground", True)
        End Sub
    Code:
       Private Function GetAverageColor1(ByVal bm As Bitmap) As Color
    
            If bm.PixelFormat <> PixelFormat.Format24bppRgb Then
                MessageBox.Show("Image was not 24bppRgb")
                Return Color.Black
            End If
            Dim bounds As New Rectangle(0, 0, bm.Width, bm.Height)
            Dim bmd As BitmapData = bm.LockBits(bounds, ImageLockMode.ReadOnly, PixelFormat.Format24bppRgb)
            ' The stride is the width of 1 row of pixels in bytes. As 1 pixels requires 3 bytes of color   
            ' information, you would think this would always be 3 * bm.Width - But it isn't. Each row of  
            ' pixels is aligned so that it starts at a 4 byte boundary, this is done by padding rows with   
            ' extra bytes if required. (might be 8 byte boundary on x64)          
            Dim stride As Integer = bmd.Stride
            ' An array to store the color information:  
            Dim pixels(bmd.Stride * bm.Height - 1) As Byte
            ' Copy it all out of the bitmap:  
            Marshal.Copy(bmd.Scan0, pixels, 0, pixels.Length)
            bm.UnlockBits(bmd)
            Dim totalR As UInteger
            Dim totalG As UInteger
            Dim totalB As UInteger
            For y As Integer = 0 To bm.Height - 1
                For x As Integer = 0 To bm.Width - 1
                    ' Get the index of a pixel in the array.  
                    ' The index will be the number of bytes in all the rows above the pixel,   
                    ' which is (y * stride)   
                    ' plus the number of bytes in all the pixels to the left of it   
                    ' so add x*3:  
                    Dim index As Integer = (y * stride) + (x * 3)
                    totalB += pixels(index)
                    totalG += pixels(index + 1)
                    totalR += pixels(index + 2)
                Next
            Next
            ' Average the components  
            Dim pixelCount As Integer = bm.Width * bm.Height
            Dim averageR As Integer = CType(totalR \ pixelCount, Integer)
            Dim averageG As Integer = CType(totalG \ pixelCount, Integer)
            Dim averageB As Integer = CType(totalB \ pixelCount, Integer)
            Return Color.FromArgb(averageR, averageG, averageB)
        End Function
    Code:
       Public Shared Function ConvertTo24bpp(ByVal img As Bitmap) As Bitmap
            Dim bmp As Bitmap = New Bitmap(img.Width, img.Height, PixelFormat.Format24bppRgb)
            Using gr As Graphics = Graphics.FromImage(bmp)
                gr.DrawImage(img, New Rectangle(0, 0, img.Width, img.Height))
            End Using
            Return bmp
        End Function

  2. #2
    Bad man! ident's Avatar
    Join Date
    Mar 2009
    Location
    Cambridge
    Posts
    5,398

    Re: Getting Average Color of Form BackgroundImage

    Is your enter/return key broken?

  3. #3

    Thread Starter
    PowerPoster
    Join Date
    Feb 2016
    Location
    Tennessee
    Posts
    2,437

    Re: Getting Average Color of Form BackgroundImage

    Meaning?

  4. #4
    Bad man! ident's Avatar
    Join Date
    Mar 2009
    Location
    Cambridge
    Posts
    5,398

    Re: Getting Average Color of Form BackgroundImage

    Maybe consider making code readable. Instead dumping everything line by line.

  5. #5

    Thread Starter
    PowerPoster
    Join Date
    Feb 2016
    Location
    Tennessee
    Posts
    2,437

    Re: Getting Average Color of Form BackgroundImage

    Thanks for the suggestion my friend. I will keep that in mind for future posts.

  6. #6
    Bad man! ident's Avatar
    Join Date
    Mar 2009
    Location
    Cambridge
    Posts
    5,398

    Re: Getting Average Color of Form BackgroundImage

    That code was written 10 years ago.

  7. #7

    Thread Starter
    PowerPoster
    Join Date
    Feb 2016
    Location
    Tennessee
    Posts
    2,437

    Re: Getting Average Color of Form BackgroundImage

    Amazing isn't it? It still works great!

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  



Click Here to Expand Forum to Full Width