This is sort of connected to an earlier post I made about get the average background color of a control or image. You can find that post here. This one selects the Foreground color (black or white) based on the background color.
When getting the average background color (in my case the background color of the wallpaper under a control), once in a while the foreground color was difficult to read because of the two color combinations (foreground and background color). So I searched on the net and found the code posted below...
If you would like to see the original post for the code below, you can view it here
Code:
Public Function IdealTextColor(ByVal bg As Color) As Color
Dim nThreshold As Integer = 105
Dim bgDelta As Integer = Convert.ToInt32((bg.R * 0.299) + (bg.G * 0.587) + (bg.B * 0.114))
Dim foreColor As Color = If((255 - bgDelta < nThreshold), Color.Black, Color.White)
Return foreColor
End Function
I have a small clock I wrote as part of a larger program and it sits on the desktop. And as I mentioned, sometimes it's hard to read. But using the code below solved the issue. When the background color of the control becomes light enough, the forecolor will switch to black. And I thought I would share it because I think it's pretty neat
Below is the sub that calls all the other code.
Code:
Public Sub ListviewForm_BackgroundImageChanged(sender As Object, e As EventArgs) Handles Me.BackgroundImageChanged
If LittleTime.Visible Then
rk.SetValue("ClockAutoBackground", True)
Dim NewBmp As Object = rk.GetValue("LastWallpaper") ' get current wallpaper from the registry
If CStr(NewBmp) <> "" Then
Dim bmp As Bitmap = New Bitmap(CStr(NewBmp))
bmp = CropBitmap(bmp)
If bmp IsNot Nothing Then
bmp = ConvertTo24bpp(bmp)
Dim clr As Color = GetAverageColor1(bmp)
LittleTime.BackColor = clr
LittleTime.MyTime.ForeColor = IdealTextColor(clr)
rk.SetValue("ClockAutoBackground", True)
bmp.Dispose()
End If
End If
End If
End Sub
Convert the bitmap to 24bpp so it will work with the Get Average Color function
Code:
Public Shared Function ConvertTo24bpp(ByVal img As Bitmap) As Bitmap
Dim bmp As Bitmap = New Bitmap(img.Width, img.Height, System.Drawing.Imaging.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
And finally the cropping of the bitmap so I only get the color of the wallpaper underneath the clock. You can do it without cropping, but you will get back the Average Color of the whole wallpaper and that's not as good of a color match for what's under the control
Code:
Private MyRect As Rectangle
Private Function CropBitmap(ByRef bmp As Bitmap) As Bitmap
MyRect.X = ScreenWidth - LittleTime.Width
MyRect.Y = LittleTime.Height
MyRect.Width = LittleTime.Width
MyRect.Height = LittleTime.Height
Dim cropped As Bitmap = bmp.Clone(MyRect, bmp.PixelFormat)
Return cropped
End Function