Fading Windows

Here I show two ways to apply a cool fade effect to your windows: one using the Win32 API function AnimateWindow, and the other using SetLayeredWindowAttributes.

AnimateWindow

You just have to specify the handle to the window, how long it takes to play the animation, and the type of animation. For example, you could do a fade-in when opening and a fade-out when closing the window like this:

.IF uMsg == WM_INITDIALOG

    ; fade-in
    INVOKE AnimateWindow, hWnd, 500, AW_BLEND

.ELSEIF uMsg == WM_CLOSE

    ; fade-out
    INVOKE AnimateWindow, hWnd, 500, AW_BLEND OR AW_HIDE
    ; close
    INVOKE EndDialog, hWnd, NULL

.ENDIF

Pros:

  • Very easy to do.
  • In addition to AW_BLEND, it has other effects.

Cons:

  • Some controls aren't rendered correctly during fade-in.
  • You can't specify the final transparency of the window.

Example in MASM32: fade-1.zip.

SetLayeredWindowAttributes

This method takes a bit more work, here's how I did the fade-in and fade-out:

.IF uMsg == WM_INITDIALOG

    ; find address of SetWindowAttributes
    INVOKE LoadLibrary, ADDR sDllName
    .IF eax != NULL
        push eax ; for FreeLibrary
        INVOKE GetProcAddress, eax, ADDR sApiName
        mov SetLayeredWindowAttribs, eax
        .IF SetLayeredWindowAttribs != NULL
            ; make the window invisible
            push LWA_ALPHA
            push 0
            push 0
            push hWnd
            call [SetLayeredWindowAttribs]
            ; show it
            INVOKE ShowWindow, hWnd, SW_SHOW
            ; redraw it
            INVOKE RedrawWindow, hWnd, NULL, NULL, RDW_UPDATENOW
        .ENDIF
        call FreeLibrary
    .ENDIF

    ; fade-in
    .IF SetLayeredWindowAttribs != NULL
        push esi
        mov esi, 0
        .WHILE esi < 255
            inc esi
            push LWA_ALPHA
            push esi
            push 0
            push hWnd
            call [SetLayeredWindowAttribs]
            INVOKE Sleep, 1
        .ENDW
        pop esi
    .ENDIF

.ELSEIF uMsg == WM_CLOSE

    ; fade-out
    .IF SetLayeredWindowAttribs != NULL
        push esi
        mov esi, 255
        .WHILE esi > 0
            dec esi
            push LWA_ALPHA
            push esi
            push 0
            push hWnd
            call [SetLayeredWindowAttribs]
            INVOKE Sleep, 1
        .ENDW
        pop esi
    .ENDIF
    ; close
    INVOKE EndDialog, hWnd, NULL

.ENDIF

Pros:

  • Renders all controls correctly during fade-in (AnimateWindow doesn't, AFAIK).
  • You can specify the final transparency of the window.

Cons:

  • Not as easy as AnimateWindow.
  • AnimateWindow has other types of effects.

Example in MASM32: fade-2.zip.

Comments