Before diving into this, I should clarify something that hasn't been brought up in earlier posts: the DWM only redirects top-level HWNDs. Thus, a Multiple Document Interface (MDI) application (Microsoft Management Console, mmc.exe, is a good example of this) will have its overall top-level HWND, with it's internal child HWNDs, composited as a single entity. The application process draws the child HWNDs, and their non-client areas, as it always has.
For the purposes of a discussion on redirection, there are really three types of windows that are of interest: GDI-rendered windows, DirectX-rendered windows, and windows rendered by a mix of DirectX and GDI. Let's discuss these in turn.
Today and for the near future, most applications use and will continue to use GDI to render their content. Traditionally, GDI applications were notified when a part of their window became unoccluded, and were asked to repaint that portion of the window. Under the DWM, that window is redirected, and the following happens:
There are a few implications of the above that are worth calling out.
Unlike GDI applications, DirectX applications of course can natively render into the DirectX pixel format that the DWM expects. They also have a very clear indication of when they're done rendering due to the requirements that they call Present(). As such, DirectX applications only need a single window buffer to manage their redirection. DirectX window redirection is handled by having the DirectX system, when it's determining what surface to provide the app with to render to, make calls to the DWM in order to share a surface between the DirectX client application process, and the DWM process. This "shared surface" support is unique to DirectX atop the WDDM, and is another key reason why WDDM is an absolute requirement for running the DWM.
When a Present() happens to such a surface, the DWM is notified that there are dirtied surfaces that need to be composited to form the desktop, and that serves as an indication to perform a composition. (It's actually a fair bit more complicated than that, but this description certainly provides the gist of it.)
Certain DirectX-based applications have much more stringent scheduling requirements (for instance, video applications), and there are public APIs provided that allow the application to get a lot more information, and more control, over when they should render based upon the rendering schedule of the desktop compositor. That will be covered more in a future topic.
Finally, WPF (Avalon) applications are DirectX applications, so they render just as the DX applications described above render.
The other reasonably common rendering to a top level window involves mixing DirectX and GDI. There are two forms of "mixing" here, one is perfectly fine, and the other is problematic.
The form of mixing that is fine is when there is a window tree of the top level HWND and child HWNDs (and further children, etc), where each individual HWND is either rendered by DirectX or by GDI. In this situation, the redirection component of the DWM forms its own "composition tree" where each node in the tree represents a node or a set of "homogenously rendered nodes" in the "window tree" rooted at the top level HWND. Rendering occurs by having each of these render to their own surface, and then compositing this tree of surfaces to the desktop. Thus, mixed DirectX and GDI rendering works well, so long as the boundary between them is at least at the child HWND level.
The form of mixing that doesn't work well is when an application uses DirectX and GDI to target the same HWND. This has never been a supported scenario with DirectX, but there have been scenarios where it has happened to work. Under the DWM, this is much more problematic, because there can be no guarantee of ordering between the DirectX and the GDI rendering. This is most troublesome when GDI and DirectX are not only rendering to the same HWND, but to overlapping areas of the same HWND. As such, this usage pattern is not supported. Note that there is an alternative that can often work for an application -- DirectX is capable of handing back a DC to a DirectX surface, and applications can perform GDI rendering to that DC. From the DWM's perspective, that DirectX surface remains purely rendered by DirectX, and all is well.
Lastly, since we're on the redirection topic, one particularly dangerous practice is writing to the screen, either through the use of GetDC(NULL) and writing to that, or attempting to do XOR rubber-band lines, etc. There are two big reasons that writing to the screen is bad: