Update bitmap in picturebox with data from a socket I'm working on a screen sharing project, and I receive a small block of images from a Socket constantly. I need to update them on a certain initial desktop bitmap I have.

After receiving every block, it copies its pixels according to a specific position (X and Y parameters), which is how the initial image gets updated. But then comes the part where I need to display it on a Picturebox. I handle the Paint event and redrawing it all again. The entire initial image is pretty big (1920X1080 in my case).

private void MainScreenThread()
{
    ReadData();//reading data from socket.
    initial = bufferToJpeg();//first intial full screen image.
    pictureBox1.Paint += pictureBox1_Paint;//activating the paint event.
    while (true)
    {
        int pos = ReadData();
        x = BlockX();//where to draw :X
        y = BlockY();//where to draw :Y
        Bitmap block = bufferToJpeg();//constantly reciving blocks.
        Draw(block, new Point(x, y));//applying the changes-drawing the block on the big initial image.

        this.Invoke(new Action(() =&gt;
        {
            pictureBox1.Refresh();//updaing the picturebox for seeing results.
            // this.Text = ((pos / 1000).ToString() + "KB");
        }));
    }
}

private void pictureBox1_Paint(object sender, PaintEventArgs e)
{
    lock (initial)
    {
        e.Graphics.DrawImage(initial, pictureBox1.ClientRectangle); //draws at picturebox's bounds
    }
}


Because I'm aiming at high speed performance (it's kind of a real-time project), I would like to know if there's any method to draw the block itself on the picturebox instead of drawing the whole initial bitmap again. Plus, scaling it to the Picuturebox bounds  seems too inefficient to me.

The picturebox itself is not resizeable - it has a fixed width and height. But I need to scale the initial Bitmap every time (after processing the blocks) so it will fit the picturbox bounds to allow the client to see the full image. Despite their screen resolution, it's lower than the shared screen resolution (the server screen which is getting captured and shared).

This is my drawing method (works extremely fast, copying block with memcpy):

private unsafe void Draw(Bitmap bmp2, Point point)
{
    lock (initial)
    {  
        BitmapData bmData = initial.LockBits(new Rectangle(0, 0, initial.Width, initial.Height), System.Drawing.Imaging.ImageLockMode.WriteOnly, initial.PixelFormat);
        BitmapData bmData2 = bmp2.LockBits(new Rectangle(0, 0, bmp2.Width, bmp2.Height), System.Drawing.Imaging.ImageLockMode.ReadOnly, bmp2.PixelFormat);
        IntPtr scan0 = bmData.Scan0;
        IntPtr scan02 = bmData2.Scan0;
        int stride = bmData.Stride;
        int stride2 = bmData2.Stride;
        int Width = bmp2.Width;
        int Height = bmp2.Height;
        int X = point.X;
        int Y = point.Y;

        scan0 = IntPtr.Add(scan0, stride * Y + X * 3);//setting the pointer to the requested line
        for (int y = 0; y &lt; Height; y++)
        {
            memcpy(scan0, scan02 ,(UIntPtr)(Width * 3));//copy one line

            scan02 = IntPtr.Add(scan02, stride2);//advance pointers
            scan0 = IntPtr.Add(scan0, stride);//advance pointers//
        }


        initial.UnlockBits(bmData);
        bmp2.UnlockBits(bmData2);
    }
If your blocks don't change size, why not create adjacent picture boxes so that you update each one individually?

If that isn't providing enough performance, remove the picture box altogether and create a custom user control where you override the OnPaint method and do your drawing inside of it.

This way, the you will pass your user control an array of bitmaps to draw and where to draw them and, when OnPaint gets called, you simply use DrawImage() to place each one at the appropriate location. 

No need for you to join the bitmaps manually.

Should a new a image arrive and you want to force redrawing, simply call Invalidate() on the user control which will force OnPaint to be called. 
This can be optimized even further as Invalidate can be called only on a specific region of your control, allowing you to only redraw the parts that are necessary.