kyuseo의 게임 프로그래밍

LoadWindowPos, SaveWindowPos :: 윈도우의 위치를 저장 & 복구 하는 함수 본문

C++ 개발

LoadWindowPos, SaveWindowPos :: 윈도우의 위치를 저장 & 복구 하는 함수

kyuseo 2007. 10. 24. 19:50

개요..

 

윈도우즈 프로그래밍을 하다 보면 윈도우의 위치를 마지막에 유저가 사용한 위치로 복구하여 유저의 편의성을 올려줄 경우가 많이 있습니다.

 

레지스트리를 이용하여 윈도우의 위치를 저장하고 복구하는 것이 일반적이고 알고리즘 자체도 단순하긴 하지만 자칫 잘못하면 보이지 않는 위치에 윈도우를 복구하는 경우가 종종 있습니다.

   

오류 가능성을 줄이고 사용하기 편리하도록 함수를 만들어 보았습니다. 

 

다운로드

 

 

 

코드

 

1. 로드 & 세이브 함수 작성 (MainFrm.cpp)

 

void LoadWindowPos( CWnd& rWnd, LPCSTR szName, BOOL bResize );

void SaveWindowPos( CWnd& rWnd, LPCSTR szName );

 

void LoadWindowPos( CWnd& rWnd, LPCSTR szName, BOOL bResize )

{

    CString strReg = AfxGetApp()->GetProfileString( "Position", szName );

 

    if( strReg.IsEmpty() == TRUE )

    {

        rWnd.CenterWindow();

    }

    else

    {

        CRect rcReg;

        sscanf_s( strReg, "%d %d %d %d", &rcReg.left, &rcReg.top, &rcReg.right, &rcReg.bottom );

 

        CSize Size = rcReg.Size();

 

        // 사용할스크린크기를구한다. (멀티,듀얼 모니터에서도올바르게작동됨)

        // (! 멀티,듀얼 모니터의경우작업바계산은싱글모니터에서만정상작동된다.)

 

        // 싱글모니터로먼저검사한다.

        CRect rc;

 

        CRect rcScreen( 0, 0, GetSystemMetrics( SM_CXFULLSCREEN ), GetSystemMetrics( SM_CYFULLSCREEN ) );

        if( rc.IntersectRect( &rcScreen, &rcReg ) == FALSE )

        {

            // 듀얼모니터로설정한다.

            rcScreen.left = GetSystemMetrics( SM_XVIRTUALSCREEN );

            rcScreen.top = GetSystemMetrics( SM_YVIRTUALSCREEN );

            rcScreen.right = rcScreen.left + GetSystemMetrics( SM_CXVIRTUALSCREEN );

            rcScreen.bottom = rcScreen.top + GetSystemMetrics( SM_CYVIRTUALSCREEN );

        }

 

        // 현재윈도우의크기를그대로이용하고자한다면...

        if( bResize == FALSE )

        {

            CRect rcPos;

            rWnd.GetWindowRect( rcPos );

            Size = rcPos.Size();

        }

 

        // 1차우측, 하단위주로검사&설정한다.

        rcReg.right = rcReg.left + Size.cx;

        rcReg.bottom = rcReg.top + Size.cy;

 

        if( rcReg.right > rcScreen.right ) rcReg.left -= rcReg.right - rcScreen.right;

        if( rcReg.bottom > rcScreen.bottom ) rcReg.top -= rcReg.bottom - rcScreen.bottom ;

 

        // 2차좌측상단위주로검사&설정한다.

        if( rcReg.left < rcScreen.left ) rcReg.left = rcScreen.left;

        if( rcReg.top < rcScreen.top ) rcReg.top = rcScreen.top;

 

        rcReg.right = rcReg.left + Size.cx;

        rcReg.bottom = rcReg.top + Size.cy;

 

        rWnd.MoveWindow( rcReg );

    }

}

 

void SaveWindowPos( CWnd& rWnd, LPCSTR szName )

{

    CRect rcPos;

    rWnd.GetWindowRect( rcPos );

 

    CString str;

    str.Format( "%d %d %d %d", rcPos.left, rcPos.top, rcPos.right, rcPos.bottom );

    AfxGetApp()->WriteProfileString( "Position", szName, str );

}

 

 

2. 윈도우에 저장 & 복구 기능 추가 (MainFrm.cpp)

 

int CMainFrame::OnCreate(LPCREATESTRUCT lpCreateStruct)

{

    …

    …

 

    LoadWindowPos( *this, "MyMainFrame", TRUE );

 

    

    …

}

 

void CMainFrame::OnClose()

{

    …

    …

 

    SaveWindowPos( *this, "MyMainFrame" );

 

    …

    …

}