News:

Masm32 SDK description, downloads and other helpful links
Message to All Guests

Main Menu

Resizing background picture in MDI client ?

Started by K_F, December 28, 2013, 07:22:30 PM

Previous topic - Next topic

K_F

Solved.. added a WM_SIZE section
CPU usage doesn't even feature on idle, and around 1.5% max on full throttle -and when I'm whipping the mouse around like crazy it's about 5%
Quote;------------------------------------------------
   ;
   ;------------------------------------------------
   .ElseIf uMsg == WM_ERASEBKGND
      Return   TRUE                        ;

   .ElseIf   uMsg ==   WM_PAINT
        invoke   BeginPaint, hWnd, ADDR ps
        mov      hDC,eax

      invoke   GetClientRect, hWnd, ADDR Rct

       invoke   StretchBlt, hDC,0,0,ps.rcPaint.right,ps.rcPaint.bottom,
                         memDC,0,0,700,390,SRCCOPY

        invoke   EndPaint, hWnd,ADDR ps
      Return   TRUE                        ;


   .Elseif uMsg == WM_SIZE
        invoke   GetDC, hWnd                     ;Lets get a Display Context for the
        mov      hDC, eax                     ;hWnd Client area.

      invoke   GetClientRect, hWnd, ADDR Rct

       invoke   StretchBlt, hDC,0,0,Rct.right,Rct.bottom,
                         memDC,0,0,700,390,SRCCOPY

      invoke   ReleaseDC,hWnd,hDC
      Return   TRUE                        ;
                        ;

Thanks for the help..
:t :t :t
'Sire, Sire!... the peasants are Revolting !!!'
'Yes, they are.. aren't they....'

dedndave

perhaps you misunderstood me
you use InvalidateRect/InvalidateRgn to cause all or a portion of the client to be added to the update region

http://msdn.microsoft.com/en-us/library/windows/desktop/dd145002%28v=vs.85%29.aspx
http://msdn.microsoft.com/en-us/library/windows/desktop/dd145003%28v=vs.85%29.aspx

ValidateRect/ValidateRgn do the opposite - they remove a portion from the update region
in other words, they tell the OS that part is ok as is, or has been updated

http://msdn.microsoft.com/en-us/library/windows/desktop/dd145194%28v=vs.85%29.aspx
http://msdn.microsoft.com/en-us/library/windows/desktop/dd145195%28v=vs.85%29.aspx

the problem with the CPU running like that is that it continually sends WM_PAINT messages
because it thinks it still needs to be updated
so - when you draw it, you want to use ValidateRect   :t

dedndave

as for WM_SIZE....
because it's an MDI window, some messages that are sent to the frame proc must exit via DefFrameProc,
even if you have handled them - this is so that the MDIClient proc will also get a chance to work it's magic

WM_SIZE is one of those messages
so, do not RET with EAX = 0 when done processing WM_SIZE
instead, pass it to DefFrameProc (the value in EAX doesn't matter)

WM_COMMAND is similar
if you process a menu click - fine, return 0
but, if it's a menu click that is not one of your menu ID's, send it to DefFrameProc
otherwise, the menu that handles MDIChildren won't be updated or allowed to select different windows

dedndave

this one seems to work under XP
we need someone to test it under Windows 7, with and without Aero Glass theme

rather than processing WM_PAINT, i set the MDIClient class background to NULL and process WM_ERASEBKGND   :P

K_F

Quote from: dedndave on December 30, 2013, 09:14:02 AM
perhaps you misunderstood me
you use InvalidateRect/InvalidateRgn to cause all or a portion of the client to be added to the update region

http://msdn.microsoft.com/en-us/library/windows/desktop/dd145002%28v=vs.85%29.aspx
http://msdn.microsoft.com/en-us/library/windows/desktop/dd145003%28v=vs.85%29.aspx

ValidateRect/ValidateRgn do the opposite - they remove a portion from the update region
in other words, they tell the OS that part is ok as is, or has been updated

http://msdn.microsoft.com/en-us/library/windows/desktop/dd145194%28v=vs.85%29.aspx
http://msdn.microsoft.com/en-us/library/windows/desktop/dd145195%28v=vs.85%29.aspx

the problem with the CPU running like that is that it continually sends WM_PAINT messages
because it thinks it still needs to be updated
so - when you draw it, you want to use ValidateRect   :t
I'm with that..  :biggrin:
I got rid of the Invalidate... but the Validate's didn't work properly either, so with WM_SIZE I didn't have to use any of them.
This is with the simple window though... I'll start back on the MDI window later today..
:t
'Sire, Sire!... the peasants are Revolting !!!'
'Yes, they are.. aren't they....'

K_F

New wndProc.. (simple window)
Quote;------------------------------------------------------------------------------
;
;------------------------------------------------------------------------------
Window1Procedure Proc hWnd:HWND, uMsg:ULONG, wParam:WPARAM, lParam:LPARAM



   ;------------------------------------------------
   ;Call me Lord Creator
   ;------------------------------------------------
   .If uMsg == WM_CREATE

      invoke   GetModuleHandle, NULL            ;Need the App Instance for the
      mov      hInst, eax                     ;Bitmap load, Otherwise the
        invoke   LoadBitmap, hInst, IDB_BMP         ;BMP does not appear.
        mov      hBmp, eax                     ;BMP handle

        invoke   GetDC, hWnd                     ;Lets get a Display Context for the
        mov      hDC, eax                     ;hWnd Client area.

        invoke   CreateCompatibleDC, hDC             ;Lets also get a 'duplicate' DC in memory
        mov    memDC,eax                     ;You BLT from here to the window

        invoke   SelectObject, memDC, hBmp           ;'put' the bitmap into the 'back' DC

        invoke   ReleaseDC, hWnd, hDC                ;release the window's dc again


   ;------------------------------------------------
   ;
   ;------------------------------------------------
   .ElseIf   uMsg ==   WM_PAINT
        invoke   BeginPaint, hWnd, ADDR ps
        mov      hDC,eax

      invoke   GetClientRect, hWnd, ADDR Rct

       invoke   StretchBlt, hDC,0,0,Rct.right,Rct.bottom,
                         memDC,0,0,700,390,SRCCOPY

        invoke   EndPaint, hWnd,ADDR ps
;      Return   TRUE                        ;


   .Elseif uMsg == WM_SIZE
        invoke   GetDC, hWnd                     ;Lets get a Display Context for the
        mov      hDC, eax                     ;hWnd Client area.

      invoke   GetClientRect, hWnd, ADDR Rct

       invoke   StretchBlt, hDC,0,0,Rct.right,Rct.bottom,
                         memDC,0,0,700,390,SRCCOPY

      invoke   ReleaseDC,hWnd,hDC
;      Return   TRUE                        ;


   ;------------------------------------------------
   ;
   ;------------------------------------------------
   .ElseIf uMsg == WM_CLOSE

      Invoke IsModal, hWnd
      .If Eax
         Invoke EndModal, hWnd, IDCANCEL
         Mov Eax, TRUE ;Return TRUE
         Ret
      .EndIf
   .EndIf

   Xor Eax, Eax   ;Return FALSE
   Ret
Window1Procedure EndP
'Sire, Sire!... the peasants are Revolting !!!'
'Yes, they are.. aren't they....'

dedndave


six_L

Quotewe need someone to test it under Windows 7, with and without Aero Glass theme
i tested that it's ok under windows 7 p.
Say you, Say me, Say the codes together for ever.

K_F

#23
Quote from: dedndave on December 30, 2013, 09:30:16 PM
did you try the program i posted ?
Yes it worked .. very neat,

I looked at it and used similar methods to come up with this.. which works 'so far'  :biggrin:
:t
'Sire, Sire!... the peasants are Revolting !!!'
'Yes, they are.. aren't they....'

K_F

Goto thinking... miracles happen  :icon_mrgreen:

MSDN says that uMsg==WM_ERASEBKGND is sent by WM_PAINT or something similar.

So I thought.. I'm painting the background 2x... So I deleted the WM_PAINT section.. and all works the same...so far

Wierd ??
an old dog can still learn new tricks

Just comment out the WM_PAINT section..
Quote;   .ElseIf   uMsg ==   WM_PAINT
;        invoke   BeginPaint, hClient, ADDR ps      ;MDI Client as usual
;        mov      hDC,eax                        ;

;      invoke   GetClientRect, hClient, ADDR Rct   ;We want to redraw the whole client
;                                       ;area so we use the RECT parameters
;                                       ;instead of the PAINTSTRUCT rect.
;                                       ;The PS rect sometimes does not give
;                                       ;you the whole client area.

;       invoke   StretchBlt, hDC,0,0,Rct.right,Rct.bottom,   ;Scale the original bitmap
;                         memDC,0,0,560,316,SRCCOPY         ;into the MDI client area

;        invoke   EndPaint, hClient,ADDR ps         ;Goodbye to MDI cleint DC

Although it's not clear in MSDN.. it seems that uMsg==WM_ERASEBKGND is sent whenever a window portion is 'Invalidated'.
Placing the draw client under the  uMsg==WM_ERASEBKGND section  seems to work OK..
Anybody got other ideas on this ?
'Sire, Sire!... the peasants are Revolting !!!'
'Yes, they are.. aren't they....'

dedndave

if you look at my code.....
subclass the MDIClient control (window)
use SetClassLong to set the MDIClient background brush to NULL (up to you to erase the background)
in the ClientProc, i handle the WM_ERASEBKGND message, not WM_PAINT

advantages....
no BeginPaint/EndPaint
no PAINTSTRUCT (the hDC for WM_ERASEBKGND is in wParam)

i also set the background brush to NULL in the frame class - not sure if it really matters, though

if you notice, there is no flicker when sizing the window

K_F

Funny enough.. although I didn't intend it.. I think I ended up doing 'exactly' what you've done .. maybe adapted to easycode without subclassing.
Well.. that's at least what i think I've done  :P

But I couldn't have done it without your example..
I picked up on the WM_ERASEBKGND here
Thanks
:t
'Sire, Sire!... the peasants are Revolting !!!'
'Yes, they are.. aren't they....'