question

SindhuH-2474 avatar image
0 Votes"
SindhuH-2474 asked SindhuH-2474 commented

Increasing performance of windows forms with multiple controls

Hello,

I am currently developing a windows app, which has at least 400 controls and a lot more events and actions.
However, now that I have started coding, with 25 controls itself, the winform is beginning to decline its performance by showing lag, while executing and also while coding especially while dragging and dropping controls on the designer tab (takes at least 15 seconds to display).
I have been using multiple forms, but still facing the same problem.

Please help me guide you to overcome this error.

Thank you in advance.

windows-forms
· 10
5 |1600 characters needed characters left characters exceeded

Up to 10 attachments (including images) can be used with a maximum of 3.0 MiB each and 30.0 MiB total.

What sort of controls are they ?
If they are similar to Buttons or PictureBoxes, it would be better to draw them (in Paint event), with Double-Buffering to avoid flickering

1 Vote 1 ·

Hello,
Thank you you for your reply, these are mainly the pictureboxes, and imageslists. Because my software has lot of customized pictures, i am in need of pictureboxes, can i know if there are any alternatives to pictureboxes that will not be load on the project or memory.

Thank you in advance

0 Votes 0 ·

Hey Castorix31,

If I use customized controls instead of picture boxes, how is that going to affect my software performance?
The only issue is that I have a lot of controls, which are picture boxes on which I am creating events like a mouse click, mouse hover, and many other things.
The end goal is to create a software (that is huge and has lots of controls) without a lag and is light on memory usage

Thank you in advance

0 Votes 0 ·

For performance, the best way is to use Direct2D (P/Invoke), but it needs more code
The second best method is by embedding WPF controls (both Direct2D and WPF use hardware acceleration) with ElementHost Class
I did a test with Image Class with 400 images in a ScrollViewer
and the display is as fast as if there were 2/3 controls : Scroll-Viewer.gif


1 Vote 1 ·
Show more comments

1 Answer

Castorix31 avatar image
0 Votes"
Castorix31 answered Castorix31 edited

From comments,
a test with 400 images in a ScrollViewer embedded with ElementHost (+ a click event) =>

134333-scrollviewer-test.jpg

Add the 4 references first :

     ' Add reference to PresentationFramework
     ' Add reference to PresentationCore
     ' Add reference to WindowsBase

     ' Add reference to WindowsFormsIntegration
     ' Add Imports System.Windows.Forms.Integration

Test :

 Imports System.Windows.Forms.Integration
    
 Public Class Form1
    
     Dim nImageWidth As Double = 0
     Dim nImageHeight As Double = 0
    
     Private Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load
         If True Then
             Dim nWidth As Double = 600, nHeight As Double = 400
    
             Dim gridMain As System.Windows.Controls.Grid = New System.Windows.Controls.Grid()
             gridMain.Background = System.Windows.Media.Brushes.White
    
             Dim scrollViewer1 As New System.Windows.Controls.ScrollViewer
             scrollViewer1.HorizontalScrollBarVisibility = System.Windows.Controls.ScrollBarVisibility.Auto
    
             Dim grid1 As New System.Windows.Controls.Grid
             grid1.HorizontalAlignment = System.Windows.HorizontalAlignment.Left
             grid1.VerticalAlignment = System.Windows.VerticalAlignment.Top
    
             Dim sTempPath As String = System.IO.Path.GetTempPath()
             sTempPath = String.Concat(sTempPath, "Hulk.jpg")
             Using wc As New System.Net.WebClient()
                 wc.DownloadFile(New Uri("https://i.ibb.co/WVfdcJb/hulk.jpg"), sTempPath)
             End Using
             Dim sImageFileName As String = sTempPath
             Dim bmp1 As System.Windows.Media.Imaging.BitmapImage = New System.Windows.Media.Imaging.BitmapImage(New Uri(sImageFileName, UriKind.Absolute))
             sTempPath = System.IO.Path.GetTempPath()
             sTempPath = String.Concat(sTempPath, "Schtroumpfette.jpg")
             Using wc As New System.Net.WebClient()
                 wc.DownloadFile(New Uri("https://i.ibb.co/52Lz2mk/Schtroumpfette.jpg"), sTempPath)
             End Using
             sImageFileName = sTempPath
             Dim bmp2 As System.Windows.Media.Imaging.BitmapImage = New System.Windows.Media.Imaging.BitmapImage(New Uri(sImageFileName, UriKind.Absolute))
             Dim imgArray() As System.Windows.Controls.Image = New System.Windows.Controls.Image(400 - 1) {}
             nImageWidth = Math.Max(bmp1.PixelWidth, bmp2.PixelWidth)
             nImageHeight = Math.Max(bmp1.PixelHeight, bmp2.PixelHeight)
             Dim i As Integer = 0
             Dim nX As Double = 0, nY As Double = 0
             Do While (i < imgArray.Length)
                 Dim img1 As System.Windows.Media.Imaging.BitmapImage
                 If (i Mod 2 = 0) Then
                     img1 = bmp1
                 Else
                     img1 = bmp2
                 End If
                 imgArray(i) = New System.Windows.Controls.Image()
                 imgArray(i).Source = img1
                 imgArray(i).Width = nImageWidth
                 imgArray(i).Height = nImageHeight
                 imgArray(i).Margin = New System.Windows.Thickness(nX, nY, 0, 0)
                 imgArray(i).HorizontalAlignment = System.Windows.HorizontalAlignment.Left
                 imgArray(i).VerticalAlignment = System.Windows.VerticalAlignment.Top
                 nX += nImageWidth
                 grid1.Children.Add(imgArray(i))
                 AddHandler imgArray(i).MouseDown, AddressOf Image_MouseDown
                 i += 1
                 If (i Mod 10 = 0) Then
                     nY += nImageHeight
                     nX = 0
                 End If
             Loop
    
             scrollViewer1.Content = grid1
             gridMain.Children.Add(scrollViewer1)
    
             Dim elementHost1 As ElementHost = New ElementHost() With {
                 .Child = gridMain,
                 .Location = New System.Drawing.Point(10, 10),
                 .Size = New System.Drawing.Size(CInt(nWidth), CInt(nHeight)),
                 .BackColor = System.Drawing.Color.Yellow
             }
             Me.Controls.Add(elementHost1)
             Return
         End If
     End Sub
    
     Private Sub Image_MouseDown(ByVal sender As Object, ByVal e As System.Windows.Input.MouseButtonEventArgs)
         Dim img As System.Windows.Controls.Image = TryCast(sender, System.Windows.Controls.Image)
         If (e.LeftButton = 1) Then
             Dim nX As Double = img.Margin.Left / nImageWidth
             Dim nY As Double = img.Margin.Top / nImageHeight
             MessageBox.Show(String.Format("Image ({0} - {1}) clicked", nX.ToString(), nY.ToString()), "Information", MessageBoxButtons.OK, MessageBoxIcon.Asterisk)
         End If
     End Sub
 End Class



scrollviewer-test.jpg (116.6 KiB)
5 |1600 characters needed characters left characters exceeded

Up to 10 attachments (including images) can be used with a maximum of 3.0 MiB each and 30.0 MiB total.