elhacker.net cabecera Bienvenido(a), Visitante. Por favor Ingresar o Registrarse
¿Perdiste tu email de activación?.

 

 


Tema destacado: Los 10 CVE más críticos (peligrosos) de 2020


+  Foro de elhacker.net
|-+  Programación
| |-+  Programación General
| | |-+  .NET (C#, VB.NET, ASP) (Moderador: kub0x)
| | | |-+  Error Genérico en GDI+
0 Usuarios y 1 Visitante están viendo este tema.
Páginas: [1] Ir Abajo Respuesta Imprimir
Autor Tema: Error Genérico en GDI+  (Leído 4,100 veces)
bybaal

Desconectado Desconectado

Mensajes: 52


Ver Perfil
Error Genérico en GDI+
« en: 9 Abril 2023, 08:22 am »

Hola tengo esta función para convertir un bitmap a icono y en algunas ocasiones ocurre la excepción 'Error Genérico en GDI+' en la última línea, alguna idea de que pueda estar pasando

Código:
    Public Function ToIcon(Image As Image,
                                  Width As Integer,
                                  Height As Integer,
                                  Optional MakeTransparent As Boolean = False,
                                  Optional Transparent As Color = Nothing) As Icon
        ToIcon = Nothing
        If IsNothing(Transparent) Then Transparent = Color.White
        Dim thumb As Bitmap = CType(Image.GetThumbnailImage(Width, Height, Nothing, IntPtr.Zero), Bitmap)
        If MakeTransparent Then thumb.MakeTransparent(Transparent)
        ToIcon = Icon.FromHandle(thumb.GetHicon())
    End Function


En línea

LlopoRobot

Desconectado Desconectado

Mensajes: 116


Un instante, una mente al unísono


Ver Perfil
Re: Error Genérico en GDI+
« Respuesta #1 en: 9 Abril 2023, 17:45 pm »

La excepción 'Error Genérico en GDI+' suele ocurrir cuando hay un problema con los recursos de GDI+ del sistema. Es posible que se esté produciendo una fuga de memoria o que se esté utilizando demasiada memoria.

Para solucionar este problema, puedes intentar liberar los recursos de memoria de GDI+ llamando al método Dispose en la imagen de vista previa y en el objeto Bitmap, así:

Código
  1. Public Function ToIcon(Image As Image,
  2.                        Width As Integer,
  3.                        Height As Integer,
  4.                        Optional MakeTransparent As Boolean = False,
  5.                        Optional Transparent As Color = Nothing) As Icon
  6.    ToIcon = Nothing
  7.    If IsNothing(Transparent) Then Transparent = Color.White
  8.    Dim thumb As Bitmap = CType(Image.GetThumbnailImage(Width, Height, Nothing, IntPtr.Zero), Bitmap)
  9.    If MakeTransparent Then thumb.MakeTransparent(Transparent)
  10.    ToIcon = Icon.FromHandle(thumb.GetHicon())
  11.    thumb.Dispose()
  12.    Image.Dispose()
  13. End Function

Además, asegúrate de que la imagen y el objeto Bitmap se estén utilizando dentro de un bloque Using o se estén liberando adecuadamente en otro lugar del código.


En línea

I'm woman baby. Can't you tell?
bybaal

Desconectado Desconectado

Mensajes: 52


Ver Perfil
Re: Error Genérico en GDI+
« Respuesta #2 en: 10 Abril 2023, 20:28 pm »

Ya lo agregué, pero sigue el problema, por eso aquí comparto todo el código para que se vea mejor cual puede ser el problema

Código
  1. Public Class Form1
  2.    Private WithEvents tmrRefresh As New Timer With {.Enabled = True, .Interval = 1}
  3.  
  4.    Private Sub tmrRefresh_Tick(sender As Object, e As EventArgs) Handles tmrRefresh.Tick
  5.        Dim gr As Graphics
  6.        Dim bmp As Bitmap = My.Resources.white
  7.        Dim br As New SolidBrush(Color.Black)
  8.        Dim free As String = AutoScaleSize(My.Computer.Info.AvailablePhysicalMemory, 2, False)
  9.        Dim x() As String
  10.        Dim por As Integer
  11.        Dim colBar As Color
  12.  
  13.        Text = free
  14.        x = Split(free)
  15.        free = x(0)
  16.        x = Split(free, ",")
  17.        If Len(x(0)) = 1 Then x(0) = $"0{x(0)}"
  18.        If Len(x(1)) = 1 Then x(1) = $"0{x(1)}"
  19.  
  20.        gr = Graphics.FromImage(bmp)
  21.        gr.DrawString($"{x(0)},", New Font("Arial", 12, FontStyle.Bold), br, New PointF(0, 0))
  22.        gr.DrawString(x(1), New Font("Arial", 12, FontStyle.Bold), br, New PointF(0, 14))
  23.  
  24.        por = Porciento(My.Computer.Info.AvailablePhysicalMemory,
  25.                        My.Computer.Info.TotalPhysicalMemory)
  26.        Select Case por
  27.            Case Is >= 75 : colBar = Color.Green
  28.            Case Is >= 50 : colBar = Color.Yellow
  29.            Case Is >= 25 : colBar = Color.Orange
  30.            Case Is >= 0 : colBar = Color.Red
  31.        End Select
  32.        gr.DrawLine(New Pen(colBar, 5), 28, 2, 28, 30)
  33.  
  34.        Icon = ToIcon(bmp, 32, 32)
  35.  
  36.        bmp.Dispose()
  37.        gr.Dispose()
  38.        br.Dispose()
  39.  
  40.    End Sub
  41.  
  42. End Class
  43.  
  44. Module modExtras
  45.  
  46.    Public Function Porciento(Parte As ULong,
  47.                              Total As ULong,
  48.                              Optional Round As Boolean = False,
  49.                              Optional Decimals As Integer = 0) As Double
  50.        Porciento = 0
  51.        Try
  52.            Porciento = Parte * 100 / Total
  53.            If Round Then Porciento = Math.Round(Porciento, Decimals)
  54.        Catch ex As Exception
  55.        End Try
  56.    End Function
  57.  
  58.    Public Function ToIcon(Image As Image,
  59.                           Width As Integer,
  60.                           Height As Integer,
  61.                           Optional MakeTransparent As Boolean = False,
  62.                           Optional Transparent As Color = Nothing) As Icon
  63.        ToIcon = Nothing
  64.        'Try
  65.        If IsNothing(Transparent) Then Transparent = Color.White
  66.        Dim thumb As Bitmap = CType(Image.GetThumbnailImage(Width, Height, Nothing, IntPtr.Zero), Bitmap)
  67.        If MakeTransparent Then thumb.MakeTransparent(Transparent)
  68.        ToIcon = Icon.FromHandle(thumb.GetHicon())
  69.        thumb.Dispose()
  70.        Image.Dispose()
  71.        'Catch ex As Exception
  72.        'End Try
  73.    End Function
  74.  
  75.    Public Function AutoScaleSize(Bytes As Decimal,
  76.                                  Optional Decimals As Integer = 2,
  77.                                  Optional FullName As Boolean = False,
  78.                                  Optional BaseMil As Boolean = False) As String
  79.        AutoScaleSize = ""
  80.        Try
  81.            Dim C As Integer
  82.            Dim b As Decimal = Bytes
  83.            Dim Div As Integer
  84.  
  85.            If BaseMil Then Div = 1000 Else Div = 1024
  86.            Do While b >= Div
  87.                b /= Div
  88.                C += 1
  89.            Loop
  90.            b = Math.Round(b, Decimals)
  91.            Select Case C
  92.                Case 0 : If FullName Then Return b & " Bytes" Else Return b & " B"
  93.                Case 1 : If FullName Then Return b & " KiloBytes" Else Return b & " KB"
  94.                Case 2 : If FullName Then Return b & " MegaBytes" Else Return b & " MB"
  95.                Case 3 : If FullName Then Return b & " GigaBytes" Else Return b & " GB"
  96.                Case 4 : If FullName Then Return b & " TeraBytes" Else Return b & " TB"
  97.                Case 5 : If FullName Then Return b & " PetaBytes" Else Return b & " PB"
  98.                Case 6 : If FullName Then Return b & " ExaBytes" Else Return b & " EB"
  99.                Case 7 : If FullName Then Return b & " ZettaBytes" Else Return b & " ZB"
  100.                Case 8 : If FullName Then Return b & " YottaBytes" Else Return b & " YB"
  101.                Case Else : If FullName Then Return Bytes & " Bytes" Else Return Bytes & " B"
  102.            End Select
  103.        Catch ex As Exception
  104.        End Try
  105.    End Function
  106.  
  107. End Module
  108.  
  109.  
« Última modificación: 10 Abril 2023, 20:36 pm por bybaal » En línea

Elektro Enjuto

Desconectado Desconectado

Mensajes: 121



Ver Perfil WWW
Re: Error Genérico en GDI+
« Respuesta #3 en: 30 Agosto 2023, 19:23 pm »

El tamaño y las características de la imagen de recurso "white" son desconocidos, así que no soy capaz de reproducir el problema que describes.

De todas formas, estás añadiendo una carga altísima y totalmente innecesaria al utilizar procedimientos de dibujado manual, generando una lentitud de respuesta en tu aplicación, y por culpa de un intervalo de temporizador tan reducido, todo para hacer cosas que son facilmente accesibles mediante las propiedades del Form...

Primeramente, ¿por qué asignas la imagen de icono más de una única vez?. En cada iteración del temporizador vuelves a pasar por todo el procedimiento de copia de imagen y resscalado solo para volver a reasignar la misma imagen una y otra vez, sin descanso.

Lo mismo haces al dibujar texto en la barra de título del form, cosa que puedes asignar mediante la propiedad Form.Text, y eso siempre estará mucho más optimizado que cualquier procedimiento casero de dibujado como el que estás utilizando.

Por último aquí te dejo una versión simplificada de la función ToIcon, sin recurrir a la función GetThumbnailImage para no deteriorar la calidad inicial pre-obtención de icono:

Código
  1.    <DebuggerStepThrough>
  2. Public Function ToIcon(image As Image, size As Size,
  3.                       Optional makeTransparent As Boolean = False,
  4.                       Optional transparentColor As Color = Nothing) As Icon
  5.  
  6.    Using clone As New Bitmap(image, size)
  7.        If makeTransparent AndAlso (transparentColor <> Color.Empty) Then
  8.            clone.MakeTransparent(transparentColor)
  9.        End If
  10.  
  11.        Return Icon.FromHandle(clone.GetHicon())
  12.    End Using
  13.  
  14. End Function

Saludos.
« Última modificación: 30 Agosto 2023, 19:30 pm por Elektro Enjuto » En línea

@%$& #$ %&#$, ¡hay que decirlo más!.
Páginas: [1] Ir Arriba Respuesta Imprimir 

Ir a:  

Mensajes similares
Asunto Iniciado por Respuestas Vistas Último mensaje
Hacer un Lanzador Genérico
Programación Visual Basic
Rumaca 2 1,999 Último mensaje 14 Enero 2007, 13:19 pm
por Gorky
Error genérico en GDI+
.NET (C#, VB.NET, ASP)
Crazy.sx 4 14,412 Último mensaje 30 Diciembre 2012, 06:03 am
por Crazy.sx
Algoritmo genérico
Programación C/C++
pilo312 0 1,552 Último mensaje 28 Mayo 2016, 00:24 am
por pilo312
Monitor genérico que no es PnP
Windows
apok26 1 2,370 Último mensaje 15 Septiembre 2016, 03:47 am
por KenshiroOne
soap generico
Programación Visual Basic
adla 2 1,883 Último mensaje 19 Diciembre 2020, 08:24 am
por BlackZeroX
WAP2 - Aviso Legal - Powered by SMF 1.1.21 | SMF © 2006-2008, Simple Machines