Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What System.Drawing classes count as GDI objects?

Tags:

c#

winforms

gdi+

I have been having difficulties understanding which exact objects from the System.Drawing namespace actually contribute to the system total GDI object count. For instance, do Matrix objects count? GraphicsPath? Pen?

In order to test this, I ran the following code on Form initialization.

public partial class Form1 : Form
{
    Timer timer = new Timer();
    List<Pen> pens = new List<Pen>();

    public Form1()
    {
        InitializeComponent();

        var r = new Random();
        for (int i = 0; i < 1000; i++)
        {
            var p = new Pen(
                Color.FromArgb(r.Next(255), r.Next(255), r.Next(255)),
                (float)r.NextDouble() * 10);
            pens.Add(p);
        }

        timer.Interval = 30;
        timer.Tick += timer_Tick;
        timer.Start();
    }

    void timer_Tick(object sender, EventArgs e)
    {
        panel1.Invalidate();
    }

    private void panel1_Paint(object sender, PaintEventArgs e)
    {
        for (int i = 0; i < pens.Count; i++)
        {
            e.Graphics.DrawLine(pens[i], (int)(20 + i * 0.1), 20, (int)(50 + i * 0.1), 50);
        }
    }
}

I was surprised to find that my application GDI object count was 32 (measured with Task Manager > Details > GDI objects column). This was true even if I kept the list around and forced the Paint event to draw individual lines with each of the generated pens. I even tried creating random colors to ensure that nothing got reused and still the GDI count kept steady at 32.

There are a lot of posts worrying about caching and reusing Pen instances and other objects, but it is not clear to me whether all System.Drawing objects contribute to this count.

Maybe modern GDI+ implementations are actually lazy and delay allocation only to when you are actually drawing something?

Update: GSerg pointed out that the MSDN official documentation says

When you use GDI+, you don't have to be as concerned with handles and device contexts as you do when you use GDI.

It seems that GDI+ abstracts over GDI handle and avoids using them as much as possible. This is also consistent with reports elsewhere that seem to indicate that GDI+ only actually creates a GDI handle when it absolutely has to. For example, a Bitmap is only backed by a handle if you call methods that require a handle to exist, e.g. GetHBitmap().

It seems that, at least in modern GDI+, Pen, Brush and many other System.Drawing objects do not actually contribute to the total GDI object count. Of course, in C# they still leak unmanaged memory if they are not disposed, since they are backed by unmanaged GDI+ objects, but native memory is not such a harsh mistress as GDI memory.

If this current interpretation is not contested, I will move it to an answer over the next few days.

like image 427
glopes Avatar asked Apr 20 '18 11:04

glopes


People also ask

What are GDI objects?

GDI Objects (Graphics Device Interface) is a core windows component responsible for representing graphical objects and outputting them to devices such as printers or monitors. For every window or application that is open, it uses up GDI Objects.

Which of the following are the GDI derived classes?

Here's a list of the GDI derived classes: CBitmap—A bitmap is an array of bits in which one or more bits correspond to each display pixel. You can use bitmaps to represent images, and you can use them to create brushes. CBrush—A brush defines a bitmapped pattern of pixels that is used to fill areas with color.

What is GDI handles?

What are GDI Handles? GDI stands for Graphical Device Interface and every process that displays graphical objects and formatted text uses it. By default, each process has a limit of 10 000 GDI handles. Just like when CPU usage is high or available RAM is low, your computer can become unstable, when GDI handles run low.


1 Answers

The following objects cause a GDI handle to be created:

  • Bitmap
  • Brush
  • DC
  • Enhanced Metafile
  • Enhanced Metafile DC
  • Font
  • Memory DC
  • Metafile
  • Metafile DC
  • Palette
  • Pen
  • Extended Pen
  • Region

This list was drawn up by using the information from here: https://learn.microsoft.com/en-gb/windows/desktop/SysInfo/gdi-objects

like image 194
Cronan Avatar answered Oct 24 '22 04:10

Cronan