Sign in to follow this  
Sparx82

Display an array of pixels

Recommended Posts

I receive an image over network (proprietary protocol) and then I'd like to display this in a window. Actually, it's not only one image, it's more or less a capture of another monitor, so there are (depending on the available bandwith and the resolution) up to 60 images per second.

I'd like to use DirectX for that because I have to resize this image according to the size of the window. So I receive an image with let's say 800x600 pixels. I do have all the RGB values then in an array. What's the best (aka fastest) way to display that using DirectX so the image will be resized according to the window (which is resizeable by the user)?

 

I'm programming C++ and use the plain WinAPI. I haven't done much using DirectX (and didn't really understand the stuff I did :-) so your help is greatly appreciated.

 

Thanks!

Share this post


Link to post
Share on other sites

Use DXGI to capture the screen then you can send updates of screen changes as change rectangles. 

 

This is the most efficient way I know of to motion capture a windows desktop. See: https://msdn.microsoft.com/en-gb/library/windows/desktop/hh404487(v=vs.85).aspx

 

Edit: just thought I'd mention that I'm pointing this out as you seemed like youre sending raw images (correct me if I'm wrong), this will not scale and your connection will quickly be bogged down. Take a look at the link above for an optimal solution for both ends of the connection... 

Edited by braindigitalis

Share this post


Link to post
Share on other sites

@Josh

 

Thanks, I'll start as you suggested, more questions will follow for sure :-)

 

@braindigitalis

Thanks as well but I only need the receiving side, the capture side is hardware and part of a remote desktop system. Normally the receiving side is hardware as well but we need a software client now. We're using different compression algorithms as well but for the beginning I'm happy when I can display the raw image stream.

Share this post


Link to post
Share on other sites

You don't even need directX, honestly. The plain windows API has StretchDIBits and friends -- It's not super fast, but if all you're doing is rendering one image to scale, it still might be the faster solution since it will avoid all the extra overhead of setting up DirectX and shuffling all those frames one at a time over the PCIe bus, extra kernel-mode switches, etc.

 

3D APIs are fast, but they have overhead. Its not a given for tiny workloads that the speedup will outpace what it costs you in extra overhead.

Share this post


Link to post
Share on other sites

I would guess that something with that is fishy -- as I said, its not super fast, but I know for certain that it can keep up with 800x600x32bit color at more than 60fps, because I've done it before, circa 2004 on one core with about half the speed of any single core we have today. Unless they've routed GDI et al through DriectX under the hood these days and that's made some use-cases slower (and it may well be), I can't imagine why StretchDIBits would have trouble keeping up. That's my experience at least, you probably know better than I what to expect given the source/destination formats you're dealing with; I just think its suspect that StretchDIBits is the bottleneck from what I know.

Share this post


Link to post
Share on other sites

I would guess that something with that is fishy -- as I said, its not super fast, but I know for certain that it can keep up with 800x600x32bit color at more than 60fps, because I've done it before, circa 2004 on one core with about half the speed of any single core we have today. Unless they've routed GDI et al through DriectX under the hood these days and that's made some use-cases slower (and it may well be), I can't imagine why StretchDIBits would have trouble keeping up. That's my experience at least, you probably know better than I what to expect given the source/destination formats you're dealing with; I just think its suspect that StretchDIBits is the bottleneck from what I know.


_All_ rendering on Windows is routed through DirectX, period, without exception. They don't even make non-DirectX graphics drivers anymore.

The GDI functions used to have special drivers that would hand-optimize various calls, possibly using the dedicated 2D render unit on the graphics hardware (which don't exist on most modern hardware anymore).

Since those drivers don't exist for new hardware and aren't supported at all anyway by Windows Vista and up, most of the GDI routines are now just basic no-brain software implementations that only route through DirectX at the lowest levels (e.g. blit to a texture, render quad). The actual scaling and format manipulation is mostly all in software and the actual texture blitting is likely not even close to as fast as a naive hand-written version would be. GDI is dead (and unlike many other such claims that are a bit premature... no, GDI really is completely dead). Don't use it. If you need plain 2D rendering use Direct2D, otherwise use Direct3D. There are a bunch of libraries that provide simple 2D rendering and compositing and use the most appropriate hardware backend for a multiple platforms, like SDL2, SFML, Allegro, etc.

More information on GDI and its dead-ness since Vista
Benchmarks of GDI on Vista and up showing it's far slower now

There's plenty of other easily searchable articles online about this all too, should you care.

Share this post


Link to post
Share on other sites

Is it absolutely necessary to recieve and display the images at 60fps?  At this rate it's likely that the network itself will become the most significant bottleneck (particularly if you're doing this over a WAN connection), and latency (as opposed to bandwidth) will prevent you ever achieving it.  What are your typical worst-case ping times between two machines involved in this?  That will give you a solid indication of the absolute best performance you're going to get from the network, and from there you can adjust the method you use to display the images at the recieving side.

 

Even if you're entirely on a good LAN, 60fps still seems overkill.  For example, Microsoft's own RDP limits the frame rate to 30fps (https://support.microsoft.com/kb/2885213) and is perfectly usable.

Share this post


Link to post
Share on other sites

Thanks for all the answers!

 

@mhagain: The transmitter does have a bandwidth limit setting and the framerate will be chosen so the traffic is within this limit. So the 60Hz are not always needed (and achieved). Normally all the stuff is running on a dedicated LAN. Because we use hardware transmitters and receivers normally and want to give the user the best achievable experience, 60Hz are requiered as long as possible. He shouldn't notice that his PC is not under his desk but somewhere in a system room on the other side of the building.

 

The REAL bottleneck I have experienced is the receiving of the network packets. Windows (winsock) can handle up to about 200-250Mbps (at least my implementation :-). This is not so much and I'm going to try to use WinPCAP later.

 

I'm going to have a look at Direct2D as well as I don't need any 3D stuff at all. What I forgot the mention: There should be some kind of anti aliasing as well. What I mean: When I receive an image with, for example, an Excel sheet inside, the black borders of the cells should be visible at every scaling factor which rules out the "just delete the pixels" scaling method.

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this