tags:

views:

562

answers:

3

Using the DwmExtendFrameIntoClientArea API call with Aero Glass enabled works just fine. However, I want it to work when Aero Glass is disabled as well, like how it works in the Windows control panel:

Notice how the frame has extended into the client area, even though Aero Glass is disabled? When I make the DwmExtendFrameIntoClientArea API call in my application, the returned HRESULT is definitely not success, and my application ends up looking like this:

Normally, with Aero Glass enabled, the border stretches down to underneath the navigation buttons, like in the control panel. How do I do this? DwmExtendFrameIntoClientArea clearly isn't working.

By the way, if it is relevant, my application is a WPF application.

A: 

This article should be of help. cheers, AR

Alain Rist
I'm sorry, but that article has nothing to do with my problem.
Alex
Sorry to have lost your time :-( I thought that the handling of WM_NCHITTEST in C# would set you on a good track :-)
Alain Rist
I'm not dealing with hit testing and relevant functionality here, though, I'm trying to achieve the look and feel of the DwmExtendFrameIntoClientArea behavior on a system where Aero Glass is disabled. The article you linked to is a decent article, but unfortunately, it's irrelevant to my problem. I thank you for your effort, though.
Alex
+2  A: 

You have to paint it to be frame-like yourself.

You have to use DwmIsCompositionEnabled to check if the DWM is enabled and handle WM_DWMCOMPOSITIONCHANGED to detect DWM state changed.

Then you have to have to separate way of drawing the window, if DWM is enabled you use DwmExtendFrameIntoClientArea, if it's disabled you draw the "frame" yourself.

I have no idea how to duplicate the Aero frame in WPF (in my app I have my own color scheme and I'm not using the Auro frame).

This is annoying but when the DWM is disabled the system falls back to XP-style drawing and none of the DWM's services work - even those that aren't related to the glass effect.

Nir
A: 

Nir's answer is correct; when composition is disabled you have to draw that area yourself.

i can show you the code i have in the paint handler of the panel at the top of my form - the panel normally responsible for drawing the 0x00000000 transparent black to make the glass appear:

Psuedo-code:

procedure DrawGlassHeaderArea(g: Graphics; r: Rectangle; IsFormFocused: Boolean);
const
   clFakeGlassColor = $00EAD1B9;  //(185, 209, 234) This is the fake foreground glass color (for use when composition is disabled)
   clFakeGlassColorUnfocused = $00F2E4D7; //(242, 228, 215) This is the fake background glass color (for use when composition is disabled)
begin
   if Dwm.IsCompositionEnabled then
   begin
      g.FillRectangle(r, 0x00000000); //fill rectangle with transparent black
   end
   else
      //Composition disabled; fake it like Microsoft does

      //The color to use depends if the form has focused or not
      Color glassColor;
      if (IsFormFocused) then
         c = clFakeGlassColor 
      else
         c = clFakeGlassColorUnfocused;

      g.FillRectangle(r, glassColor); //fill rectangle with fake color


      //Now we have to draw the two accent lines along the bottom
      Color edgeHighlight = ColorBlend(Colors.White, glassColor, 0.33); //mix 33% of glass color to white
      Color edgeShadow = ColorBlend(Colors.Black, glassColor, 0.33); //mix 33% of glass color to black

      //Draw highlight as 2nd-last row:
      g.DrawLine(edgeHighlight, Point(r.Left, r.Bottom-2), Point(r.Right, r.Bottom-2);

      //Draw shadow on the very last row:
      g.DrawLine(edgeHighlight, Point(r.Left, r.Bottom-1), Point(r.Right, r.Bottom-1);
   end;
end;

Sample usage

procedure MyForm.PaintBox1Paint(PaintEventArgs e)
begin
   DrawGlassHeaderArea(e.Graphics, PaintBox1.ClientRectangle, this.HasFocus); 
end;
Ian Boyd