Il existe une autre méthode beaucoup plus rapide et beaucoup plus pratique. Si vous regardez les constructeurs de Bitmap, vous en trouverez un qui prendra IntPtr comme dernier paramètre. IntPtr est destiné à contenir des données de pixels. Alors, comment l'utilisez-vous?
Dim imageWidth As Integer = 1920
Dim imageHeight As Integer = 1080
Dim fmt As PixelFormat = PixelFormat.Format32bppRgb
Dim pixelFormatSize As Integer = Image.GetPixelFormatSize(fmt)
Dim stride As Integer = imageWidth * pixelFormatSize
Dim padding = 32 - (stride Mod 32)
If padding < 32 Then stride += padding
Dim pixels((stride \ 32) * imageHeight) As Integer
Dim handle As GCHandle = GCHandle.Alloc(pixels, GCHandleType.Pinned)
Dim addr As IntPtr = Marshal.UnsafeAddrOfPinnedArrayElement(pixels, 0)
Dim bitmap As New Bitmap(imageWidth, imageHeight, stride \ 8, fmt, addr)
Ce que vous avez maintenant est un tableau entier simple et un bitmap référençant la même mémoire. Toutes les modifications que vous apportez au tableau Integer affecteront directement le bitmap. Essayons cela avec une simple transformation de luminosité.
Public Sub Brightness(ByRef pixels() As Integer, ByVal scale As Single)
Dim r, g, b As Integer
Dim mult As Integer = CInt(1024.0f * scale)
Dim pixel As Integer
For i As Integer = 0 To pixels.Length - 1
pixel = pixels(i)
r = pixel And 255
g = (pixel >> 8) And 255
b = (pixel >> 16) And 255
'brightness calculation
'shift right by 10 <=> divide by 1024
r = (r * mult) >> 10
g = (g * mult) >> 10
b = (b * mult) >> 10
'clamp to between 0 and 255
If r < 0 Then r = 0
If g < 0 Then g = 0
If b < 0 Then b = 0
r = (r And 255)
g = (g And 255)
b = (b And 255)
pixels(i) = r Or (g << 8) Or (b << 16) Or &HFF000000
Next
End Sub
Vous remarquerez peut-être que je l'ai utilisé une petite astuce pour éviter de faire des mathématiques à virgule flottante dans la boucle. Cela améliore les performances un peu. Et quand vous avez terminé, vous devez nettoyer un peu bien sûr ...
addr = IntPtr.Zero
If handle.IsAllocated Then
handle.Free()
handle = Nothing
End If
bitmap.Dispose()
bitmap = Nothing
pixels = Nothing
J'ai ignoré le composant alpha ici, mais vous êtes libre d'utiliser aussi. J'ai jeté ensemble beaucoup d'outils d'édition bitmap de cette façon. Il est beaucoup plus rapide et plus fiable que Bitmap.LockBits() et le meilleur de tous, il ne nécessite aucune copie de mémoire pour commencer à éditer votre bitmap.
Le lien suivant contient des méthodes d'accès aux pixels bitmap de manière comparative. http://csharpexamples.com/fast-image-processing-c/ – turgay