zoukankan      html  css  js  c++  java
  • 窗口浮动4生1模式

    //////////////////////////scbarg.h////////////////////

    //Download by http://www.NewXing.com
    #if !defined(__SCBARG_H__)
    #define __SCBARG_H__

    #if _MSC_VER >= 1000
    #pragma once
    #endif // _MSC_VER >= 1000

    /////////////////////////////////////////////////////////////////////////
    // CSCBButton (button info) helper class

    class CSCBButton
    {
    public:
    CSCBButton();

    void Move(CPoint ptTo) {ptOrg = ptTo; };
    CRect GetRect() { return CRect(ptOrg, CSize(13, 13)); };
    void Paint(CDC* pDC);

    BOOL bPushed;
    BOOL bRaised;

    protected:
    CPoint ptOrg;
    };

    /////////////////////////////////////////////////////////////////////////
    // CSizingControlBar control bar

    #ifndef baseCCoolBar
    #define baseCCoolBar CSizingControlBar
    #endif

    class CCoolBar : public baseCCoolBar
    {
    DECLARE_DYNAMIC(CCoolBar);

    // Construction
    public:
    CCoolBar();

    // Attributes
    public:
    virtual BOOL HasGripper() const;

    // Operations
    public:

    // Overridables
    virtual void OnUpdateCmdUI(CFrameWnd* pTarget, BOOL bDisableIfNoHndler);
    virtual BOOL Create(LPCTSTR lpszWindowName, CWnd* pParentWnd,
    CSize sizeDefault, BOOL bHasGripper,
    UINT nID, DWORD dwStyle = WS_CHILD | WS_VISIBLE | CBRS_TOP);
    virtual BOOL Create(LPCTSTR lpszWindowName, CWnd* pParentWnd,
    UINT nID, DWORD dwStyle = WS_CHILD | WS_VISIBLE | CBRS_TOP);

    // Overrides
    public:
    // ClassWizard generated virtual function overrides
    //{{AFX_VIRTUAL(CCoolBar)
    //}}AFX_VIRTUAL

    // Implementation
    public:
    void SetNotifyWindow(HWND hNotifyWnd);
    HWND GetNotifyWindow() { return m_hNotifyWnd; };
    virtual ~CCoolBar();

    protected:
    // implementation helpers
    virtual void NcPaintGripper(CDC* pDC, CRect rcClient);
    virtual void NcCalcClient(LPRECT pRc, UINT nDockBarID);

    protected:
    int m_cyGripper;
    CSCBButton m_biHide;
    BOOL m_bActive; // a child has focus
    CString m_sFontFace;
    HWND m_hNotifyWnd; // 消息通知窗口,默认为父窗口

    // Generated message map functions
    protected:
    //{{AFX_MSG(CCoolBar)
    afx_msg UINT OnNcHitTest(CPoint point);
    afx_msg void OnNcLButtonUp(UINT nHitTest, CPoint point);
    afx_msg LRESULT OnSetText(WPARAM wParam, LPARAM lParam);
    afx_msg BOOL OnNotify( WPARAM wParam, LPARAM lParam, LRESULT* pResult );
    //}}AFX_MSG

    DECLARE_MESSAGE_MAP()
    };

    #endif // !defined(__SCBARG_H__)

    ////////////////////////////////////////////scbarg.cpp/////////////////////////////////

    //Download by http://www.NewXing.com
    // sizecbar.cpp : implementation file
    //

    #include "stdafx.h"

    #ifdef _DEBUG
    #define new DEBUG_NEW
    #undef THIS_FILE
    static char THIS_FILE[] = __FILE__;
    #endif

    int CALLBACK EnumFontFamProc(ENUMLOGFONT FAR *lpelf,
    NEWTEXTMETRIC FAR *lpntm,
    int FontType,
    LPARAM lParam)
    {
    UNUSED_ALWAYS(lpelf);
    UNUSED_ALWAYS(lpntm);
    UNUSED_ALWAYS(FontType);
    UNUSED_ALWAYS(lParam);

    return 0;
    }

    /////////////////////////////////////////////////////////////////////////
    // CCoolBar

    IMPLEMENT_DYNAMIC(CCoolBar, baseCCoolBar);

    CCoolBar::CCoolBar()
    {
    m_hNotifyWnd = NULL;
    m_cyGripper = 12;
    SetSCBStyle(GetSCBStyle() | SCBS_SIZECHILD);
    m_bActive = FALSE;
    CDC dc;
    dc.CreateCompatibleDC(NULL);
    m_sFontFace = (::EnumFontFamilies(dc.m_hDC,
    _T("宋体"), (FONTENUMPROC) EnumFontFamProc, 0) == 0) ?
    _T("宋体") : _T("Tahoma");
    dc.DeleteDC();
    }

    CCoolBar::~CCoolBar()
    {
    }

    BEGIN_MESSAGE_MAP(CCoolBar, baseCCoolBar)
    //{{AFX_MSG_MAP(CCoolBar)
    ON_WM_NCLBUTTONUP()
    ON_WM_NCHITTEST()
    //}}AFX_MSG_MAP
    ON_MESSAGE(WM_SETTEXT, OnSetText)
    END_MESSAGE_MAP()

    /////////////////////////////////////////////////////////////////////////
    // CCoolBar message handlers

    BOOL CCoolBar::Create(LPCTSTR lpszWindowName, CWnd* pParentWnd,
    CSize sizeDefault, BOOL bHasGripper,
    UINT nID, DWORD dwStyle)
    {
    ASSERT_VALID(pParentWnd);
    m_hNotifyWnd = pParentWnd->m_hWnd;

    return baseCCoolBar::Create(lpszWindowName, pParentWnd, sizeDefault, bHasGripper, nID, dwStyle);
    }

    BOOL CCoolBar::Create(LPCTSTR lpszWindowName,
    CWnd* pParentWnd, UINT nID,
    DWORD dwStyle)
    {
    ASSERT_VALID(pParentWnd);
    m_hNotifyWnd = pParentWnd->m_hWnd;

    return baseCCoolBar::Create(lpszWindowName, pParentWnd, nID, dwStyle);
    }

    /////////////////////////////////////////////////////////////////////////
    // Mouse Handling
    //

    void CCoolBar::OnNcLButtonUp(UINT nHitTest, CPoint point)
    {
    if (nHitTest == HTCLOSE)
    m_pDockSite->ShowControlBar(this, FALSE, FALSE); // hide

    baseCCoolBar::OnNcLButtonUp(nHitTest, point);
    }

    #ifndef COLOR_GRADIENTACTIVECAPTION
    #define COLOR_GRADIENTACTIVECAPTION 27
    #define COLOR_GRADIENTINACTIVECAPTION 28
    #define SPI_GETGRADIENTCAPTIONS 0x1008
    #endif

    void CCoolBar::NcCalcClient(LPRECT pRc, UINT nDockBarID)
    {
    CRect rcBar(pRc); // save the bar rect

    // subtract edges
    baseCCoolBar::NcCalcClient(pRc, nDockBarID);

    if (!HasGripper())
    return;

    CRect rc(pRc); // the client rect as calculated by the base class

    BOOL bHorz = (nDockBarID == AFX_IDW_DOCKBAR_TOP) ||
    (nDockBarID == AFX_IDW_DOCKBAR_BOTTOM);

    if (bHorz)
    rc.DeflateRect(m_cyGripper, 0, 0, 0);
    else
    rc.DeflateRect(0, m_cyGripper, 0, 0);

    // set position for the "x" (hide bar) button
    CPoint ptOrgBtn;
    if (bHorz)
    ptOrgBtn = CPoint(rc.left - 14, rc.top);
    else
    ptOrgBtn = CPoint(rc.right - 12, rc.top - 14);

    m_biHide.Move(ptOrgBtn - rcBar.TopLeft());

    *pRc = rc;
    }

    void CCoolBar::NcPaintGripper(CDC* pDC, CRect rcClient)
    {
    if (!HasGripper())
    return;
    #ifndef _SCB_STYLE_FLAT
    CRect gripper = rcClient;
    CRect rcbtn = m_biHide.GetRect();
    BOOL bHorz = IsHorzDocked();

    gripper.DeflateRect(1, 1);
    if (bHorz)
    { // gripper at left
    gripper.left -= m_cyGripper;
    gripper.right = gripper.left + 3;
    gripper.top = rcbtn.bottom + 3;
    }
    else
    { // gripper at top
    gripper.top -= m_cyGripper;
    gripper.bottom = gripper.top + 3;
    gripper.right = rcbtn.left - 3;
    }

    pDC->Draw3dRect(gripper, ::GetSysColor(COLOR_BTNHIGHLIGHT),
    ::GetSysColor(COLOR_BTNSHADOW));

    gripper.OffsetRect(bHorz ? 3 : 0, bHorz ? 0 : 3);

    pDC->Draw3dRect(gripper, ::GetSysColor(COLOR_BTNHIGHLIGHT),
    ::GetSysColor(COLOR_BTNSHADOW));

    m_biHide.Paint(pDC);

    #else

    // compute the caption rectangle
    BOOL bHorz = IsHorzDocked();
    CRect rcGrip = rcClient;
    CRect rcBtn = m_biHide.GetRect();
    if (bHorz)
    { // right side gripper
    rcGrip.left -= m_cyGripper + 1;
    rcGrip.right = rcGrip.left + 11;
    rcGrip.top = rcBtn.bottom + 3;
    }
    else
    { // gripper at top
    rcGrip.top -= m_cyGripper + 1;
    rcGrip.bottom = rcGrip.top + 11;
    rcGrip.right = rcBtn.left - 3;
    }
    rcGrip.InflateRect(bHorz ? 1 : 0, bHorz ? 0 : 1);

    // draw the caption background
    //CBrush br;
    COLORREF clrCptn = m_bActive ?
    ::GetSysColor(COLOR_ACTIVECAPTION) :
    ::GetSysColor(COLOR_INACTIVECAPTION);

    // query gradient info (usually TRUE for Win98/Win2k)
    BOOL bGradient = FALSE;
    ::SystemParametersInfo(SPI_GETGRADIENTCAPTIONS, 0, &bGradient, 0);

    if (!bGradient)
    pDC->FillSolidRect(&rcGrip, clrCptn); // solid color
    else
    {
    // gradient from left to right or from bottom to top
    // get second gradient color (the right end)
    COLORREF clrCptnRight = m_bActive ?
    ::GetSysColor(COLOR_GRADIENTACTIVECAPTION) :
    ::GetSysColor(COLOR_GRADIENTINACTIVECAPTION);

    // this will make 2^6 = 64 fountain steps
    int nShift = 6;
    int nSteps = 1 << nShift;

    for (int i = 0; i < nSteps; i++)
    {
    // do a little alpha blending
    int nR = (GetRValue(clrCptn) * (nSteps - i) +
    GetRValue(clrCptnRight) * i) >> nShift;
    int nG = (GetGValue(clrCptn) * (nSteps - i) +
    GetGValue(clrCptnRight) * i) >> nShift;
    int nB = (GetBValue(clrCptn) * (nSteps - i) +
    GetBValue(clrCptnRight) * i) >> nShift;

    COLORREF cr = RGB(nR, nG, nB);

    // then paint with the resulting color
    CRect r2 = rcGrip;
    if (bHorz)
    {
    r2.bottom = rcGrip.bottom -
    ((i * rcGrip.Height()) >> nShift);
    r2.top = rcGrip.bottom -
    (((i + 1) * rcGrip.Height()) >> nShift);
    if (r2.Height() > 0)
    pDC->FillSolidRect(r2, cr);
    }
    else
    {
    r2.left = rcGrip.left +
    ((i * rcGrip.Width()) >> nShift);
    r2.right = rcGrip.left +
    (((i + 1) * rcGrip.Width()) >> nShift);
    if (r2.Width() > 0)
    pDC->FillSolidRect(r2, cr);
    }
    }
    }

    // draw the caption text - first select a font
    CFont font;
    int ppi = pDC->GetDeviceCaps(LOGPIXELSX);
    int pointsize = MulDiv(96, 96, ppi); // 8.5 points at 96 ppi

    LOGFONT lf;
    BOOL bFont = font.CreatePointFont(pointsize, m_sFontFace);
    if (bFont)
    {
    // get the text color
    COLORREF clrCptnText = m_bActive ?
    ::GetSysColor(COLOR_CAPTIONTEXT) :
    ::GetSysColor(COLOR_INACTIVECAPTIONTEXT);

    int nOldBkMode = pDC->SetBkMode(TRANSPARENT);
    COLORREF clrOldText = pDC->SetTextColor(clrCptnText);

    if (bHorz)
    {
    // rotate text 90 degrees CCW if horizontally docked
    font.GetLogFont(&lf);
    font.DeleteObject();
    lf.lfEscapement = 900;
    font.CreateFontIndirect(&lf);
    }

    CFont* pOldFont = pDC->SelectObject(&font);
    CString sTitle;
    GetWindowText(sTitle);

    CPoint ptOrg = bHorz ?
    CPoint(rcGrip.left - 1, rcGrip.bottom - 3) :
    CPoint(rcGrip.left + 3, rcGrip.top - 1);

    pDC->ExtTextOut(ptOrg.x, ptOrg.y,
    ETO_CLIPPED, rcGrip, sTitle, NULL);

    pDC->SelectObject(pOldFont);
    pDC->SetBkMode(nOldBkMode);
    pDC->SetTextColor(clrOldText);
    }

    // draw the button
    m_biHide.Paint(pDC);
    #endif
    }

    UINT CCoolBar::OnNcHitTest(CPoint point)
    {
    CRect rcBar;
    GetWindowRect(rcBar);

    UINT nRet = baseCCoolBar::OnNcHitTest(point);
    if (nRet != HTCLIENT)
    return nRet;

    CRect rc = m_biHide.GetRect();
    rc.OffsetRect(rcBar.TopLeft());
    if (rc.PtInRect(point))
    return HTCLOSE;

    return HTCLIENT;
    }

    /////////////////////////////////////////////////////////////////////////
    // CCoolBar implementation helpers

    void CCoolBar::OnUpdateCmdUI(CFrameWnd* pTarget,
    BOOL bDisableIfNoHndler)
    {
    UNUSED_ALWAYS(bDisableIfNoHndler);
    UNUSED_ALWAYS(pTarget);

    if (!HasGripper())
    return;

    BOOL bNeedPaint = FALSE;

    CPoint pt;
    ::GetCursorPos(&pt);
    BOOL bHit = (OnNcHitTest(pt) == HTCLOSE);
    BOOL bLButtonDown = (::GetKeyState(VK_LBUTTON) < 0);

    BOOL bWasPushed = m_biHide.bPushed;
    m_biHide.bPushed = bHit && bLButtonDown;

    BOOL bWasRaised = m_biHide.bRaised;
    m_biHide.bRaised = bHit && !bLButtonDown;

    CWnd* pFocus = GetFocus();
    BOOL bActiveOld = m_bActive;
    m_bActive = (pFocus->GetSafeHwnd() && IsChild(pFocus));
    if (m_bActive != bActiveOld)
    bNeedPaint = TRUE;

    bNeedPaint |= (m_biHide.bPushed ^ bWasPushed) ||
    (m_biHide.bRaised ^ bWasRaised);

    if (bNeedPaint)
    SendMessage(WM_NCPAINT);
    }

    /////////////////////////////////////////////////////////////////////////
    // CSCBButton

    CSCBButton::CSCBButton()
    {
    bRaised = FALSE;
    bPushed = FALSE;
    }

    void CSCBButton::Paint(CDC* pDC)
    {
    CRect rc = GetRect();

    if (bPushed)
    pDC->Draw3dRect(rc, ::GetSysColor(COLOR_BTNSHADOW),
    ::GetSysColor(COLOR_BTNHIGHLIGHT));
    else
    if (bRaised)
    pDC->Draw3dRect(rc, ::GetSysColor(COLOR_BTNHIGHLIGHT),
    ::GetSysColor(COLOR_BTNSHADOW));

    COLORREF clrOldTextColor = pDC->GetTextColor();
    pDC->SetTextColor(::GetSysColor(COLOR_BTNTEXT));
    int nPrevBkMode = pDC->SetBkMode(TRANSPARENT);
    CFont font;
    int ppi = pDC->GetDeviceCaps(LOGPIXELSX);
    int pointsize = MulDiv(60, 96, ppi); // 6 points at 96 ppi
    font.CreatePointFont(pointsize, _T("Marlett"));
    CFont* oldfont = pDC->SelectObject(&font);

    pDC->TextOut(ptOrg.x + 3, ptOrg.y + 3, CString(_T("r"))); // x-like

    pDC->SelectObject(oldfont);
    pDC->SetBkMode(nPrevBkMode);
    pDC->SetTextColor(clrOldTextColor);
    }

    BOOL CCoolBar::HasGripper() const
    {
    #if defined(_SCB_MINIFRAME_CAPTION) || !defined(_SCB_REPLACE_MINIFRAME)
    // if the miniframe has a caption, don't display the gripper
    if (IsFloating())
    return FALSE;
    #endif //_SCB_MINIFRAME_CAPTION

    return TRUE;
    }

    LRESULT CCoolBar::OnSetText(WPARAM wParam, LPARAM lParam)
    {
    LRESULT lResult = baseCCoolBar::OnSetText(wParam, lParam);

    SendMessage(WM_NCPAINT);

    return lResult;
    }

    BOOL CCoolBar::OnNotify(WPARAM wParam, LPARAM lParam, LRESULT* pResult)
    {
    // 将WM_NOTIFY消息转交给消息通知窗口处理

    ::SendMessage(m_hNotifyWnd, WM_NOTIFY, wParam, lParam);
    *pResult = 0;

    return TRUE;
    }

    void CCoolBar::SetNotifyWindow(HWND hNotifyWnd)
    {
    m_hNotifyWnd = hNotifyWnd;
    }

    /////////////////////////////////////////////////////////sizecbar.h///////////////////////////////////////

    //Download by http://www.NewXing.com

    #if !defined(__SIZECBAR_H__)
    #define __SIZECBAR_H__

    #include <afxpriv.h> // for CDockContext
    #include <afxtempl.h> // for CTypedPtrArray

    #if _MSC_VER >= 1000
    #pragma once
    #endif // _MSC_VER >= 1000


    #if defined(_SCB_MINIFRAME_CAPTION) && !defined(_SCB_REPLACE_MINIFRAME)
    #error "_SCB_MINIFRAME_CAPTION requires _SCB_REPLACE_MINIFRAME"
    #endif

    /////////////////////////////////////////////////////////////////////////
    // CSCBDockBar dummy class for access to protected members

    class CSCBDockBar : public CDockBar
    {
    friend class CSizingControlBar;
    };

    /////////////////////////////////////////////////////////////////////////
    // CSizingControlBar control bar styles

    #define SCBS_EDGELEFT 0x00000001
    #define SCBS_EDGERIGHT 0x00000002
    #define SCBS_EDGETOP 0x00000004
    #define SCBS_EDGEBOTTOM 0x00000008
    #define SCBS_EDGEALL 0x0000000F
    #define SCBS_SHOWEDGES 0x00000010
    #define SCBS_SIZECHILD 0x00000020

    /////////////////////////////////////////////////////////////////////////
    // CSizingControlBar control bar

    #ifndef baseCSizingControlBar
    #define baseCSizingControlBar CControlBar
    #endif

    class CSizingControlBar;
    typedef CTypedPtrArray <CPtrArray, CSizingControlBar*> CSCBArray;

    class CSizingControlBar : public baseCSizingControlBar
    {
    DECLARE_DYNAMIC(CSizingControlBar);

    // Construction
    public:
    CSizingControlBar();

    virtual BOOL Create(LPCTSTR lpszWindowName, CWnd* pParentWnd,
    CSize sizeDefault, BOOL bHasGripper,
    UINT nID, DWORD dwStyle = WS_CHILD | WS_VISIBLE | CBRS_TOP);
    virtual BOOL Create(LPCTSTR lpszWindowName, CWnd* pParentWnd,
    UINT nID, DWORD dwStyle = WS_CHILD | WS_VISIBLE | CBRS_TOP);

    // Attributes
    public:
    const BOOL IsFloating() const;
    const BOOL IsHorzDocked() const;
    const BOOL IsVertDocked() const;
    const BOOL IsSideTracking() const;
    const BOOL GetSCBStyle() const {return m_dwSCBStyle;}

    // Operations
    public:
    #if defined(_SCB_REPLACE_MINIFRAME) && !defined(_SCB_MINIFRAME_CAPTION)
    void EnableDocking(DWORD dwDockStyle);
    #endif
    virtual void LoadState(LPCTSTR lpszProfileName);
    virtual void SaveState(LPCTSTR lpszProfileName);
    static void GlobalLoadState(CFrameWnd* pFrame, LPCTSTR lpszProfileName);
    static void GlobalSaveState(CFrameWnd* pFrame, LPCTSTR lpszProfileName);
    void SetSCBStyle(DWORD dwSCBStyle)
    {m_dwSCBStyle = (dwSCBStyle & ~SCBS_EDGEALL);}

    // Overridables
    virtual void OnUpdateCmdUI(CFrameWnd* pTarget, BOOL bDisableIfNoHndler);

    // Overrides
    public:
    // ClassWizard generated virtual function overrides
    //{{AFX_VIRTUAL(CSizingControlBar)
    public:
    virtual CSize CalcFixedLayout(BOOL bStretch, BOOL bHorz);
    virtual CSize CalcDynamicLayout(int nLength, DWORD dwMode);
    //}}AFX_VIRTUAL

    // Implementation
    public:
    virtual ~CSizingControlBar();

    protected:
    // implementation helpers
    UINT GetEdgeHTCode(int nEdge);
    BOOL GetEdgeRect(CRect rcWnd, UINT nHitTest, CRect& rcEdge);
    virtual void StartTracking(UINT nHitTest, CPoint point);
    virtual void StopTracking();
    virtual void OnTrackUpdateSize(CPoint& point);
    virtual void OnTrackInvertTracker();
    virtual void NcPaintGripper(CDC* pDC, CRect rcClient);
    virtual void NcCalcClient(LPRECT pRc, UINT nDockBarID);

    virtual void AlignControlBars();
    void GetRowInfo(int& nFirst, int& nLast, int& nThis);
    void GetRowSizingBars(CSCBArray& arrSCBars);
    void GetRowSizingBars(CSCBArray& arrSCBars, int& nThis);
    BOOL NegotiateSpace(int nLengthTotal, BOOL bHorz);

    protected:
    DWORD m_dwSCBStyle;
    UINT m_htEdge;

    CSize m_szHorz;
    CSize m_szVert;
    CSize m_szFloat;
    CSize m_szMinHorz;
    CSize m_szMinVert;
    CSize m_szMinFloat;
    int m_nTrackPosMin;
    int m_nTrackPosMax;
    int m_nTrackPosOld;
    int m_nTrackEdgeOfs;
    BOOL m_bTracking;
    BOOL m_bKeepSize;
    BOOL m_bParentSizing;
    BOOL m_bDragShowContent;
    UINT m_nDockBarID;
    int m_cxEdge;

    // Generated message map functions
    protected:
    //{{AFX_MSG(CSizingControlBar)
    afx_msg int OnCreate(LPCREATESTRUCT lpCreateStruct);
    afx_msg void OnNcPaint();
    afx_msg void OnNcCalcSize(BOOL bCalcValidRects, NCCALCSIZE_PARAMS FAR* lpncsp);
    afx_msg UINT OnNcHitTest(CPoint point);
    afx_msg void OnCaptureChanged(CWnd *pWnd);
    afx_msg void OnSettingChange(UINT uFlags, LPCTSTR lpszSection);
    afx_msg void OnLButtonUp(UINT nFlags, CPoint point);
    afx_msg void OnMouseMove(UINT nFlags, CPoint point);
    afx_msg void OnNcLButtonDown(UINT nHitTest, CPoint point);
    afx_msg void OnLButtonDown(UINT nFlags, CPoint point);
    afx_msg void OnLButtonDblClk(UINT nFlags, CPoint point);
    afx_msg void OnRButtonDown(UINT nFlags, CPoint point);
    afx_msg void OnWindowPosChanging(WINDOWPOS FAR* lpwndpos);
    afx_msg void OnPaint();
    afx_msg void OnClose();
    afx_msg void OnSize(UINT nType, int cx, int cy);
    //}}AFX_MSG
    afx_msg LRESULT OnSetText(WPARAM wParam, LPARAM lParam);

    DECLARE_MESSAGE_MAP()

    #ifdef _SCB_REPLACE_MINIFRAME
    friend class CSCBMiniDockFrameWnd;
    #endif //_SCB_REPLACE_MINIFRAME
    };

    #ifdef _SCB_REPLACE_MINIFRAME
    #ifndef _SCB_MINIFRAME_CAPTION
    /////////////////////////////////////////////////////////////////////////
    // CSCBDockContext dockcontext

    class CSCBDockContext : public CDockContext
    {
    public:
    // Construction
    CSCBDockContext(CControlBar* pBar) : CDockContext(pBar) {}

    // Drag Operations
    virtual void StartDrag(CPoint pt);
    };
    #endif //_SCB_MINIFRAME_CAPTION

    /////////////////////////////////////////////////////////////////////////
    // CSCBMiniDockFrameWnd miniframe

    #ifndef baseCSCBMiniDockFrameWnd
    #define baseCSCBMiniDockFrameWnd CMiniDockFrameWnd
    #endif

    class CSCBMiniDockFrameWnd : public baseCSCBMiniDockFrameWnd
    {
    DECLARE_DYNCREATE(CSCBMiniDockFrameWnd)

    // Overrides
    // ClassWizard generated virtual function overrides
    //{{AFX_VIRTUAL(CSCBMiniDockFrameWnd)
    public:
    virtual BOOL Create(CWnd* pParent, DWORD dwBarStyle);
    //}}AFX_VIRTUAL

    // Implementation
    public:
    CSizingControlBar* GetSizingControlBar();

    //{{AFX_MSG(CSCBMiniDockFrameWnd)
    afx_msg void OnNcLButtonDown(UINT nHitTest, CPoint point);
    afx_msg void OnGetMinMaxInfo(MINMAXINFO FAR* lpMMI);
    afx_msg void OnWindowPosChanging(WINDOWPOS FAR* lpwndpos);
    afx_msg void OnSize(UINT nType, int cx, int cy);
    //}}AFX_MSG
    DECLARE_MESSAGE_MAP()
    };
    #endif //_SCB_REPLACE_MINIFRAME

    #endif // !defined(__SIZECBAR_H__)

    ///////////////////////////////////////////////////sizecbar.cpp///////////////////////////////////

    //Download by http://www.NewXing.com
    // sizecbar.cpp : implementation file
    //

    #include "stdafx.h"
    #include "sizecbar.h"

    #ifdef _DEBUG
    #define new DEBUG_NEW
    #undef THIS_FILE
    static char THIS_FILE[] = __FILE__;
    #endif

    /////////////////////////////////////////////////////////////////////////
    // CSizingControlBar

    IMPLEMENT_DYNAMIC(CSizingControlBar, baseCSizingControlBar);

    CSizingControlBar::CSizingControlBar()
    {
    m_szMinHorz = CSize(33, 32);
    m_szMinVert = CSize(33, 32);
    m_szMinFloat = CSize(37, 32);
    m_szHorz = CSize(200, 200);
    m_szVert = CSize(200, 200);
    m_szFloat = CSize(200, 200);
    m_bTracking = FALSE;
    m_bKeepSize = FALSE;
    m_bParentSizing = FALSE;
    m_cxEdge = 5;
    m_bDragShowContent = FALSE;
    m_nDockBarID = 0;
    m_dwSCBStyle = 0;
    }

    CSizingControlBar::~CSizingControlBar()
    {
    }

    BEGIN_MESSAGE_MAP(CSizingControlBar, baseCSizingControlBar)
    //{{AFX_MSG_MAP(CSizingControlBar)
    ON_WM_CREATE()
    ON_WM_PAINT()
    ON_WM_NCPAINT()
    ON_WM_NCCALCSIZE()
    ON_WM_WINDOWPOSCHANGING()
    ON_WM_CAPTURECHANGED()
    ON_WM_SETTINGCHANGE()
    ON_WM_LBUTTONUP()
    ON_WM_MOUSEMOVE()
    ON_WM_NCLBUTTONDOWN()
    ON_WM_LBUTTONDOWN()
    ON_WM_LBUTTONDBLCLK()
    ON_WM_RBUTTONDOWN()
    ON_WM_NCMOUSEMOVE()
    ON_WM_NCHITTEST()
    ON_WM_CLOSE()
    ON_WM_SIZE()
    //}}AFX_MSG_MAP
    ON_MESSAGE(WM_SETTEXT, OnSetText)
    END_MESSAGE_MAP()

    // old creation method, still here for compatibility reasons
    BOOL CSizingControlBar::Create(LPCTSTR lpszWindowName, CWnd* pParentWnd,
    CSize sizeDefault, BOOL bHasGripper,
    UINT nID, DWORD dwStyle)
    {
    UNUSED_ALWAYS(bHasGripper);

    m_szHorz = m_szVert = m_szFloat = sizeDefault;
    return Create(lpszWindowName, pParentWnd, nID, dwStyle);
    }

    // preffered creation method
    BOOL CSizingControlBar::Create(LPCTSTR lpszWindowName,
    CWnd* pParentWnd, UINT nID,
    DWORD dwStyle)
    {
    // must have a parent
    ASSERT_VALID(pParentWnd);
    // cannot be both fixed and dynamic
    // (CBRS_SIZE_DYNAMIC is used for resizng when floating)
    ASSERT (!((dwStyle & CBRS_SIZE_FIXED) &&
    (dwStyle & CBRS_SIZE_DYNAMIC)));

    m_dwStyle = dwStyle & CBRS_ALL; // save the control bar styles

    // register and create the window - skip CControlBar::Create()
    CString wndclass = ::AfxRegisterWndClass(CS_DBLCLKS,
    ::LoadCursor(NULL, IDC_ARROW),
    ::GetSysColorBrush(COLOR_BTNFACE), 0);

    dwStyle &= ~CBRS_ALL; // keep only the generic window styles
    dwStyle |= WS_CLIPCHILDREN; // prevents flashing
    if (!CWnd::Create(wndclass, lpszWindowName, dwStyle,
    CRect(0, 0, 0, 0), pParentWnd, nID))
    return FALSE;

    return TRUE;
    }

    /////////////////////////////////////////////////////////////////////////
    // CSizingControlBar operations
    #if defined(_SCB_REPLACE_MINIFRAME) && !defined(_SCB_MINIFRAME_CAPTION)
    void CSizingControlBar::EnableDocking(DWORD dwDockStyle)
    {
    // must be CBRS_ALIGN_XXX or CBRS_FLOAT_MULTI only
    ASSERT((dwDockStyle & ~(CBRS_ALIGN_ANY|CBRS_FLOAT_MULTI)) == 0);
    // cannot have the CBRS_FLOAT_MULTI style
    ASSERT((dwDockStyle & CBRS_FLOAT_MULTI) == 0);
    // the bar must have CBRS_SIZE_DYNAMIC style
    ASSERT((m_dwStyle & CBRS_SIZE_DYNAMIC) != 0);

    m_dwDockStyle = dwDockStyle;
    if (m_pDockContext == NULL)
    m_pDockContext = new CSCBDockContext(this);

    // permanently wire the bar's owner to its current parent
    if (m_hWndOwner == NULL)
    m_hWndOwner = ::GetParent(m_hWnd);
    }
    #endif

    /////////////////////////////////////////////////////////////////////////
    // CSizingControlBar message handlers

    int CSizingControlBar::OnCreate(LPCREATESTRUCT lpCreateStruct)
    {
    if (baseCSizingControlBar::OnCreate(lpCreateStruct) == -1)
    return -1;

    // query SPI_GETDRAGFULLWINDOWS system parameter
    // OnSettingChange() will update m_bDragShowContent
    m_bDragShowContent = FALSE;
    ::SystemParametersInfo(SPI_GETDRAGFULLWINDOWS, 0,
    &m_bDragShowContent, 0);

    // uncomment this line if you want raised borders
    // m_dwSCBStyle |= SCBS_SHOWEDGES;

    return 0;
    }


    LRESULT CSizingControlBar::OnSetText(WPARAM wParam, LPARAM lParam)
    {
    UNUSED_ALWAYS(wParam);

    LRESULT lResult = CWnd::Default();

    if (IsFloating() &&
    GetParentFrame()->IsKindOf(RUNTIME_CLASS(CMiniDockFrameWnd)))
    {
    m_pDockBar->SetWindowText((LPCTSTR) lParam); // update dockbar
    GetParentFrame()->DelayRecalcLayout(); // refresh miniframe
    }

    return lResult;
    }

    const BOOL CSizingControlBar::IsFloating() const
    {
    return !IsHorzDocked() && !IsVertDocked();
    }

    const BOOL CSizingControlBar::IsHorzDocked() const
    {
    return (m_nDockBarID == AFX_IDW_DOCKBAR_TOP ||
    m_nDockBarID == AFX_IDW_DOCKBAR_BOTTOM);
    }

    const BOOL CSizingControlBar::IsVertDocked() const
    {
    return (m_nDockBarID == AFX_IDW_DOCKBAR_LEFT ||
    m_nDockBarID == AFX_IDW_DOCKBAR_RIGHT);
    }

    const BOOL CSizingControlBar::IsSideTracking() const
    {
    // don't call this when not tracking
    ASSERT(m_bTracking && !IsFloating());

    return (m_htEdge == HTLEFT || m_htEdge == HTRIGHT) ?
    IsHorzDocked() : IsVertDocked();
    }

    CSize CSizingControlBar::CalcFixedLayout(BOOL bStretch, BOOL bHorz)
    {
    if (bStretch) // the bar is stretched (is not the child of a dockbar)
    if (bHorz)
    return CSize(32767, m_szHorz.cy);
    else
    return CSize(m_szVert.cx, 32767);

    // dirty cast - we need access to protected CDockBar members
    CSCBDockBar* pDockBar = (CSCBDockBar*) m_pDockBar;

    // force imediate RecalcDelayShow() for all sizing bars on the row
    // with delayShow/delayHide flags set to avoid IsVisible() problems
    CSCBArray arrSCBars;
    GetRowSizingBars(arrSCBars);
    AFX_SIZEPARENTPARAMS layout;
    layout.hDWP = pDockBar->m_bLayoutQuery ?
    NULL : ::BeginDeferWindowPos(arrSCBars.GetSize());
    for (int i = 0; i < arrSCBars.GetSize(); i++)
    if (arrSCBars[i]->m_nStateFlags & (delayHide|delayShow))
    arrSCBars[i]->RecalcDelayShow(&layout);
    if (layout.hDWP != NULL)
    ::EndDeferWindowPos(layout.hDWP);

    // get available length
    CRect rc = pDockBar->m_rectLayout;
    if (rc.IsRectEmpty())
    m_pDockSite->GetClientRect(&rc);
    int nLengthTotal = bHorz ? rc.Width() + 2 : rc.Height() - 2;

    if (IsVisible() && !IsFloating() &&
    m_bParentSizing && arrSCBars[0] == this)
    if (NegotiateSpace(nLengthTotal, (bHorz != FALSE)))
    AlignControlBars();

    m_bParentSizing = FALSE;

    if (bHorz)
    return CSize(max(m_szMinHorz.cx, m_szHorz.cx),
    max(m_szMinHorz.cy, m_szHorz.cy));

    return CSize(max(m_szMinVert.cx, m_szVert.cx),
    max(m_szMinVert.cy, m_szVert.cy));
    }

    CSize CSizingControlBar::CalcDynamicLayout(int nLength, DWORD dwMode)
    {
    if (dwMode & (LM_HORZDOCK | LM_VERTDOCK)) // docked ?
    {
    if (nLength == -1)
    m_bParentSizing = TRUE;

    return baseCSizingControlBar::CalcDynamicLayout(nLength, dwMode);
    }

    if (dwMode & LM_MRUWIDTH) return m_szFloat;
    if (dwMode & LM_COMMIT) return m_szFloat; // already committed

    #ifndef _SCB_REPLACE_MINIFRAME
    // check for dialgonal resizing hit test
    int nHitTest = m_pDockContext->m_nHitTest;
    if (IsFloating() &&
    (nHitTest == HTTOPLEFT || nHitTest == HTBOTTOMLEFT ||
    nHitTest == HTTOPRIGHT || nHitTest == HTBOTTOMRIGHT))
    {
    CPoint ptCursor;
    ::GetCursorPos(&ptCursor);

    CRect rFrame, rBar;
    GetParentFrame()->GetWindowRect(&rFrame);
    GetWindowRect(&rBar);

    if (nHitTest == HTTOPLEFT || nHitTest == HTBOTTOMLEFT)
    {
    m_szFloat.cx = rFrame.left + rBar.Width() - ptCursor.x;
    m_pDockContext->m_rectFrameDragHorz.left =
    min(ptCursor.x, rFrame.left + rBar.Width() - m_szMinFloat.cx);
    }

    if (nHitTest == HTTOPLEFT || nHitTest == HTTOPRIGHT)
    {
    m_szFloat.cy = rFrame.top + rBar.Height() - ptCursor.y;
    m_pDockContext->m_rectFrameDragHorz.top =
    min(ptCursor.y, rFrame.top + rBar.Height() - m_szMinFloat.cy);
    }

    if (nHitTest == HTTOPRIGHT || nHitTest == HTBOTTOMRIGHT)
    m_szFloat.cx = rBar.Width() + ptCursor.x - rFrame.right;

    if (nHitTest == HTBOTTOMLEFT || nHitTest == HTBOTTOMRIGHT)
    m_szFloat.cy = rBar.Height() + ptCursor.y - rFrame.bottom;
    }
    else
    #endif //_SCB_REPLACE_MINIFRAME
    ((dwMode & LM_LENGTHY) ? m_szFloat.cy : m_szFloat.cx) = nLength;

    m_szFloat.cx = max(m_szFloat.cx, m_szMinFloat.cx);
    m_szFloat.cy = max(m_szFloat.cy, m_szMinFloat.cy);

    return m_szFloat;
    }

    void CSizingControlBar::OnWindowPosChanging(WINDOWPOS FAR* lpwndpos)
    {
    // force non-client recalc if moved or resized
    lpwndpos->flags |= SWP_FRAMECHANGED;

    baseCSizingControlBar::OnWindowPosChanging(lpwndpos);

    // find on which side are we docked
    m_nDockBarID = GetParent()->GetDlgCtrlID();

    if (!IsFloating())
    if (lpwndpos->flags & SWP_SHOWWINDOW)
    m_bKeepSize = TRUE;
    }

    /////////////////////////////////////////////////////////////////////////
    // Mouse Handling
    //
    void CSizingControlBar::OnLButtonDown(UINT nFlags, CPoint point)
    {
    if (m_pDockBar != NULL)
    {
    // start the drag
    ASSERT(m_pDockContext != NULL);
    ClientToScreen(&point);
    m_pDockContext->StartDrag(point);
    }
    else
    CWnd::OnLButtonDown(nFlags, point);
    }

    void CSizingControlBar::OnLButtonDblClk(UINT nFlags, CPoint point)
    {
    if (m_pDockBar != NULL)
    {
    // toggle docking
    ASSERT(m_pDockContext != NULL);
    m_pDockContext->ToggleDocking();
    }
    else
    CWnd::OnLButtonDblClk(nFlags, point);
    }

    void CSizingControlBar::OnNcLButtonDown(UINT nHitTest, CPoint point)
    {
    UNUSED_ALWAYS(point);

    if (m_bTracking || IsFloating())
    return;

    if ((nHitTest >= HTSIZEFIRST) && (nHitTest <= HTSIZELAST))
    StartTracking(nHitTest, point); // sizing edge hit
    }

    void CSizingControlBar::OnLButtonUp(UINT nFlags, CPoint point)
    {
    if (m_bTracking)
    StopTracking();

    baseCSizingControlBar::OnLButtonUp(nFlags, point);
    }

    void CSizingControlBar::OnRButtonDown(UINT nFlags, CPoint point)
    {
    if (m_bTracking)
    StopTracking();

    baseCSizingControlBar::OnRButtonDown(nFlags, point);
    }

    void CSizingControlBar::OnMouseMove(UINT nFlags, CPoint point)
    {
    if (m_bTracking)
    {
    CPoint ptScreen = point;
    ClientToScreen(&ptScreen);

    OnTrackUpdateSize(ptScreen);
    }

    baseCSizingControlBar::OnMouseMove(nFlags, point);
    }

    void CSizingControlBar::OnCaptureChanged(CWnd *pWnd)
    {
    if (m_bTracking && (pWnd != this))
    StopTracking();

    baseCSizingControlBar::OnCaptureChanged(pWnd);
    }

    void CSizingControlBar::OnNcCalcSize(BOOL bCalcValidRects,
    NCCALCSIZE_PARAMS FAR* lpncsp)
    {
    UNUSED_ALWAYS(bCalcValidRects);

    #ifndef _SCB_REPLACE_MINIFRAME
    // Enable diagonal resizing for floating miniframe
    if (IsFloating())
    {
    CFrameWnd* pFrame = GetParentFrame();
    if (pFrame != NULL &&
    pFrame->IsKindOf(RUNTIME_CLASS(CMiniFrameWnd)))
    {
    DWORD dwStyle = ::GetWindowLong(pFrame->m_hWnd, GWL_STYLE);
    if ((dwStyle & MFS_4THICKFRAME) != 0)
    {
    pFrame->ModifyStyle(MFS_4THICKFRAME, 0); // clear
    GetParent()->ModifyStyle(0, WS_CLIPCHILDREN);
    }
    }
    }
    #endif _SCB_REPLACE_MINIFRAME

    // compute the the client area
    m_dwSCBStyle &= ~SCBS_EDGEALL;

    // add resizing edges between bars on the same row
    if (!IsFloating() && m_pDockBar != NULL)
    {
    CSCBArray arrSCBars;
    int nThis;
    GetRowSizingBars(arrSCBars, nThis);

    BOOL bHorz = IsHorzDocked();
    if (nThis > 0)
    m_dwSCBStyle |= bHorz ? SCBS_EDGELEFT : SCBS_EDGETOP;

    if (nThis < arrSCBars.GetUpperBound())
    m_dwSCBStyle |= bHorz ? SCBS_EDGERIGHT : SCBS_EDGEBOTTOM;
    }

    NcCalcClient(&lpncsp->rgrc[0], m_nDockBarID);
    }

    void CSizingControlBar::NcCalcClient(LPRECT pRc, UINT nDockBarID)
    {
    CRect rc(pRc);

    rc.DeflateRect(3, 5, 3, 3);
    if (nDockBarID != AFX_IDW_DOCKBAR_FLOAT)
    rc.DeflateRect(2, 0, 2, 2);

    switch(nDockBarID)
    {
    case AFX_IDW_DOCKBAR_TOP:
    m_dwSCBStyle |= SCBS_EDGEBOTTOM;
    break;
    case AFX_IDW_DOCKBAR_BOTTOM:
    m_dwSCBStyle |= SCBS_EDGETOP;
    break;
    case AFX_IDW_DOCKBAR_LEFT:
    m_dwSCBStyle |= SCBS_EDGERIGHT;
    break;
    case AFX_IDW_DOCKBAR_RIGHT:
    m_dwSCBStyle |= SCBS_EDGELEFT;
    break;
    }

    // make room for edges only if they will be painted
    if (m_dwSCBStyle & SCBS_SHOWEDGES)
    rc.DeflateRect(
    (m_dwSCBStyle & SCBS_EDGELEFT) ? m_cxEdge : 0,
    (m_dwSCBStyle & SCBS_EDGETOP) ? m_cxEdge : 0,
    (m_dwSCBStyle & SCBS_EDGERIGHT) ? m_cxEdge : 0,
    (m_dwSCBStyle & SCBS_EDGEBOTTOM) ? m_cxEdge : 0);

    *pRc = rc;
    }

    void CSizingControlBar::OnNcPaint()
    {
    // get window DC that is clipped to the non-client area
    CWindowDC dc(this);

    CRect rcClient, rcBar;
    GetClientRect(rcClient);
    ClientToScreen(rcClient);
    GetWindowRect(rcBar);
    rcClient.OffsetRect(-rcBar.TopLeft());
    rcBar.OffsetRect(-rcBar.TopLeft());

    CDC mdc;
    mdc.CreateCompatibleDC(&dc);

    CBitmap bm;
    bm.CreateCompatibleBitmap(&dc, rcBar.Width(), rcBar.Height());
    CBitmap* pOldBm = mdc.SelectObject(&bm);

    // draw borders in non-client area
    CRect rcDraw = rcBar;
    DrawBorders(&mdc, rcDraw);

    // erase the NC background
    mdc.FillRect(rcDraw, CBrush::FromHandle(
    (HBRUSH) GetClassLong(m_hWnd, GCL_HBRBACKGROUND)));

    if (m_dwSCBStyle & SCBS_SHOWEDGES)
    {
    CRect rcEdge; // paint the sizing edges
    for (int i = 0; i < 4; i++)
    if (GetEdgeRect(rcBar, GetEdgeHTCode(i), rcEdge))
    mdc.Draw3dRect(rcEdge, ::GetSysColor(COLOR_BTNHIGHLIGHT),
    ::GetSysColor(COLOR_BTNSHADOW));
    }

    NcPaintGripper(&mdc, rcClient);

    // client area is not our bussiness :)
    dc.IntersectClipRect(rcBar);
    dc.ExcludeClipRect(rcClient);

    dc.BitBlt(0, 0, rcBar.Width(), rcBar.Height(), &mdc, 0, 0, SRCCOPY);

    ReleaseDC(&dc);

    mdc.SelectObject(pOldBm);
    bm.DeleteObject();
    mdc.DeleteDC();
    }

    void CSizingControlBar::NcPaintGripper(CDC* pDC, CRect rcClient)
    {
    UNUSED_ALWAYS(pDC);
    UNUSED_ALWAYS(rcClient);
    }

    void CSizingControlBar::OnPaint()
    {
    // overridden to skip border painting based on clientrect
    CPaintDC dc(this);
    }

    UINT CSizingControlBar::OnNcHitTest(CPoint point)
    {
    CRect rcBar, rcEdge;
    GetWindowRect(rcBar);

    if (!IsFloating())
    for (int i = 0; i < 4; i++)
    if (GetEdgeRect(rcBar, GetEdgeHTCode(i), rcEdge))
    if (rcEdge.PtInRect(point))
    return GetEdgeHTCode(i);

    return HTCLIENT;
    }

    void CSizingControlBar::OnSettingChange(UINT uFlags, LPCTSTR lpszSection)
    {
    baseCSizingControlBar::OnSettingChange(uFlags, lpszSection);

    m_bDragShowContent = FALSE;
    ::SystemParametersInfo(SPI_GETDRAGFULLWINDOWS, 0,
    &m_bDragShowContent, 0); // update
    }

    void CSizingControlBar::OnSize(UINT nType, int cx, int cy)
    {
    UNUSED_ALWAYS(nType);

    if ((m_dwSCBStyle & SCBS_SIZECHILD) != 0)
    {
    // automatic child resizing - only one child is allowed
    CWnd* pWnd = GetWindow(GW_CHILD);
    if (pWnd != NULL)
    {
    pWnd->MoveWindow(0, 0, cx, cy);
    ASSERT(pWnd->GetWindow(GW_HWNDNEXT) == NULL);
    }
    }
    }

    void CSizingControlBar::OnClose()
    {
    // do nothing: protection against accidentally destruction by the
    // child control (i.e. if user hits Esc in a child editctrl)
    }

    /////////////////////////////////////////////////////////////////////////
    // CSizingControlBar implementation helpers

    void CSizingControlBar::StartTracking(UINT nHitTest, CPoint point)
    {
    SetCapture();

    // make sure no updates are pending
    if (!m_bDragShowContent)
    RedrawWindow(NULL, NULL, RDW_ALLCHILDREN | RDW_UPDATENOW);

    m_htEdge = nHitTest;
    m_bTracking = TRUE;

    BOOL bHorz = IsHorzDocked();
    BOOL bHorzTracking = m_htEdge == HTLEFT || m_htEdge == HTRIGHT;

    m_nTrackPosOld = bHorzTracking ? point.x : point.y;

    CRect rcBar, rcEdge;
    GetWindowRect(rcBar);
    GetEdgeRect(rcBar, m_htEdge, rcEdge);
    m_nTrackEdgeOfs = m_nTrackPosOld -
    (bHorzTracking ? rcEdge.CenterPoint().x : rcEdge.CenterPoint().y);

    CSCBArray arrSCBars;
    int nThis;
    GetRowSizingBars(arrSCBars, nThis);

    m_nTrackPosMin = m_nTrackPosMax = m_nTrackPosOld;
    if (!IsSideTracking())
    {
    // calc minwidth as the max minwidth of the sizing bars on row
    int nMinWidth = bHorz ? m_szMinHorz.cy : m_szMinVert.cx;
    for (int i = 0; i < arrSCBars.GetSize(); i++)
    nMinWidth = max(nMinWidth, bHorz ?
    arrSCBars[i]->m_szMinHorz.cy :
    arrSCBars[i]->m_szMinVert.cx);
    int nExcessWidth = (bHorz ? m_szHorz.cy : m_szVert.cx) - nMinWidth;

    // the control bar cannot grow with more than the width of
    // remaining client area of the mainframe
    CRect rcT;
    m_pDockSite->RepositionBars(0, 0xFFFF, AFX_IDW_PANE_FIRST,
    reposQuery, &rcT, NULL, TRUE);
    int nMaxWidth = bHorz ? rcT.Height() - 2 : rcT.Width() - 2;

    BOOL bTopOrLeft = m_htEdge == HTTOP || m_htEdge == HTLEFT;

    m_nTrackPosMin -= bTopOrLeft ? nMaxWidth : nExcessWidth;
    m_nTrackPosMax += bTopOrLeft ? nExcessWidth : nMaxWidth;
    }
    else
    {
    // side tracking:
    // max size is the actual size plus the amount the other
    // sizing bars can be decreased until they reach their minsize
    if (m_htEdge == HTBOTTOM || m_htEdge == HTRIGHT)
    nThis++;

    for (int i = 0; i < arrSCBars.GetSize(); i++)
    {
    CSizingControlBar* pBar = arrSCBars[i];

    int nExcessWidth = bHorz ?
    pBar->m_szHorz.cx - pBar->m_szMinHorz.cx :
    pBar->m_szVert.cy - pBar->m_szMinVert.cy;

    if (i < nThis)
    m_nTrackPosMin -= nExcessWidth;
    else
    m_nTrackPosMax += nExcessWidth;
    }
    }

    OnTrackInvertTracker(); // draw tracker
    }

    void CSizingControlBar::StopTracking()
    {
    OnTrackInvertTracker(); // erase tracker

    m_bTracking = FALSE;
    ReleaseCapture();

    m_pDockSite->DelayRecalcLayout();
    }

    void CSizingControlBar::OnTrackUpdateSize(CPoint& point)
    {
    ASSERT(!IsFloating());

    BOOL bHorzTrack = m_htEdge == HTLEFT || m_htEdge == HTRIGHT;

    int nTrackPos = bHorzTrack ? point.x : point.y;
    nTrackPos = max(m_nTrackPosMin, min(m_nTrackPosMax, nTrackPos));

    int nDelta = nTrackPos - m_nTrackPosOld;

    if (nDelta == 0)
    return; // no pos change

    OnTrackInvertTracker(); // erase tracker

    m_nTrackPosOld = nTrackPos;

    BOOL bHorz = IsHorzDocked();

    CSize sizeNew = bHorz ? m_szHorz : m_szVert;
    switch (m_htEdge)
    {
    case HTLEFT: sizeNew -= CSize(nDelta, 0); break;
    case HTTOP: sizeNew -= CSize(0, nDelta); break;
    case HTRIGHT: sizeNew += CSize(nDelta, 0); break;
    case HTBOTTOM: sizeNew += CSize(0, nDelta); break;
    }

    CSCBArray arrSCBars;
    int nThis;
    GetRowSizingBars(arrSCBars, nThis);

    if (!IsSideTracking())
    for (int i = 0; i < arrSCBars.GetSize(); i++)
    {
    CSizingControlBar* pBar = arrSCBars[i];
    // make same width (or height)
    (bHorz ? pBar->m_szHorz.cy : pBar->m_szVert.cx) =
    bHorz ? sizeNew.cy : sizeNew.cx;
    }
    else
    {
    int nGrowingBar = nThis;
    BOOL bBefore = m_htEdge == HTTOP || m_htEdge == HTLEFT;
    if (bBefore && nDelta > 0)
    nGrowingBar--;
    if (!bBefore && nDelta < 0)
    nGrowingBar++;
    if (nGrowingBar != nThis)
    bBefore = !bBefore;

    // nGrowing is growing
    nDelta = abs(nDelta);
    CSizingControlBar* pBar = arrSCBars[nGrowingBar];
    (bHorz ? pBar->m_szHorz.cx : pBar->m_szVert.cy) += nDelta;

    // the others are shrinking
    int nFirst = bBefore ? nGrowingBar - 1 : nGrowingBar + 1;
    int nLimit = bBefore ? -1 : arrSCBars.GetSize();

    for (int i = nFirst; nDelta != 0 && i != nLimit; i += (bBefore ? -1 : 1))
    {
    CSizingControlBar* pBar = arrSCBars[i];

    int nDeltaT = min(nDelta,
    (bHorz ? pBar->m_szHorz.cx : pBar->m_szVert.cy) -
    (bHorz ? pBar->m_szMinHorz.cx : pBar->m_szMinVert.cy));

    (bHorz ? pBar->m_szHorz.cx : pBar->m_szVert.cy) -= nDeltaT;
    nDelta -= nDeltaT;
    }
    }

    OnTrackInvertTracker(); // redraw tracker at new pos

    if (m_bDragShowContent)
    m_pDockSite->DelayRecalcLayout();
    }

    void CSizingControlBar::OnTrackInvertTracker()
    {
    ASSERT(m_bTracking);

    if (m_bDragShowContent)
    return; // don't show tracker if DragFullWindows is on

    BOOL bHorz = IsHorzDocked();
    CRect rc, rcBar, rcDock, rcFrame;
    GetWindowRect(rcBar);
    m_pDockBar->GetWindowRect(rcDock);
    m_pDockSite->GetWindowRect(rcFrame);
    VERIFY(GetEdgeRect(rcBar, m_htEdge, rc));
    if (!IsSideTracking())
    rc = bHorz ?
    CRect(rcDock.left + 1, rc.top, rcDock.right - 1, rc.bottom) :
    CRect(rc.left, rcDock.top + 1, rc.right, rcDock.bottom - 1);

    BOOL bHorzTracking = m_htEdge == HTLEFT || m_htEdge == HTRIGHT;
    int nOfs = m_nTrackPosOld - m_nTrackEdgeOfs;
    nOfs -= bHorzTracking ? rc.CenterPoint().x : rc.CenterPoint().y;
    rc.OffsetRect(bHorzTracking ? nOfs : 0, bHorzTracking ? 0 : nOfs);
    rc.OffsetRect(-rcFrame.TopLeft());

    CDC *pDC = m_pDockSite->GetDCEx(NULL,
    DCX_WINDOW | DCX_CACHE | DCX_LOCKWINDOWUPDATE);
    CBrush* pBrush = CDC::GetHalftoneBrush();
    CBrush* pBrushOld = pDC->SelectObject(pBrush);

    pDC->PatBlt(rc.left, rc.top, rc.Width(), rc.Height(), PATINVERT);

    pDC->SelectObject(pBrushOld);
    m_pDockSite->ReleaseDC(pDC);
    }

    BOOL CSizingControlBar::GetEdgeRect(CRect rcWnd, UINT nHitTest,
    CRect& rcEdge)
    {
    rcEdge = rcWnd;
    if (m_dwSCBStyle & SCBS_SHOWEDGES)
    rcEdge.DeflateRect(1, 1);
    BOOL bHorz = IsHorzDocked();

    switch (nHitTest)
    {
    case HTLEFT:
    if (!(m_dwSCBStyle & SCBS_EDGELEFT)) return FALSE;
    rcEdge.right = rcEdge.left + m_cxEdge;
    rcEdge.DeflateRect(0, bHorz ? m_cxEdge: 0);
    break;
    case HTTOP:
    if (!(m_dwSCBStyle & SCBS_EDGETOP)) return FALSE;
    rcEdge.bottom = rcEdge.top + m_cxEdge;
    rcEdge.DeflateRect(bHorz ? 0 : m_cxEdge, 0);
    break;
    case HTRIGHT:
    if (!(m_dwSCBStyle & SCBS_EDGERIGHT)) return FALSE;
    rcEdge.left = rcEdge.right - m_cxEdge;
    rcEdge.DeflateRect(0, bHorz ? m_cxEdge: 0);
    break;
    case HTBOTTOM:
    if (!(m_dwSCBStyle & SCBS_EDGEBOTTOM)) return FALSE;
    rcEdge.top = rcEdge.bottom - m_cxEdge;
    rcEdge.DeflateRect(bHorz ? 0 : m_cxEdge, 0);
    break;
    default:
    ASSERT(FALSE); // invalid hit test code
    }
    return TRUE;
    }

    UINT CSizingControlBar::GetEdgeHTCode(int nEdge)
    {
    if (nEdge == 0) return HTLEFT;
    if (nEdge == 1) return HTTOP;
    if (nEdge == 2) return HTRIGHT;
    if (nEdge == 3) return HTBOTTOM;
    ASSERT(FALSE); // invalid edge code
    return HTNOWHERE;
    }

    void CSizingControlBar::GetRowInfo(int& nFirst, int& nLast, int& nThis)
    {
    ASSERT_VALID(m_pDockBar); // verify bounds

    nThis = m_pDockBar->FindBar(this);
    ASSERT(nThis != -1);

    int i, nBars = m_pDockBar->m_arrBars.GetSize();

    // find the first and the last bar in row
    for (nFirst = -1, i = nThis - 1; i >= 0 && nFirst == -1; i--)
    if (m_pDockBar->m_arrBars[i] == NULL)
    nFirst = i + 1;
    for (nLast = -1, i = nThis + 1; i < nBars && nLast == -1; i++)
    if (m_pDockBar->m_arrBars[i] == NULL)
    nLast = i - 1;

    ASSERT((nLast != -1) && (nFirst != -1));
    }

    void CSizingControlBar::GetRowSizingBars(CSCBArray& arrSCBars)
    {
    int nThis; // dummy
    GetRowSizingBars(arrSCBars, nThis);
    }

    void CSizingControlBar::GetRowSizingBars(CSCBArray& arrSCBars, int& nThis)
    {
    arrSCBars.RemoveAll();

    int nFirstT, nLastT, nThisT;
    GetRowInfo(nFirstT, nLastT, nThisT);

    nThis = -1;
    for (int i = nFirstT; i <= nLastT; i++)
    {
    CSizingControlBar* pBar =
    (CSizingControlBar*) m_pDockBar->m_arrBars[i];
    if (HIWORD(pBar) == 0) continue; // placeholder
    if (!pBar->IsVisible()) continue;
    if (pBar->IsKindOf(RUNTIME_CLASS(CSizingControlBar)))
    {
    if (pBar == this)
    nThis = arrSCBars.GetSize();

    arrSCBars.Add(pBar);
    }
    }
    }

    BOOL CSizingControlBar::NegotiateSpace(int nLengthTotal, BOOL bHorz)
    {
    ASSERT(bHorz == IsHorzDocked());

    int nFirst, nLast, nThis;
    GetRowInfo(nFirst, nLast, nThis);

    int nLengthAvail = nLengthTotal;
    int nLengthActual = 0;
    int nLengthMin = 2;
    int nWidthMax = 0;
    CSizingControlBar* pBar;

    for (int i = nFirst; i <= nLast; i++)
    {
    pBar = (CSizingControlBar*) m_pDockBar->m_arrBars[i];
    if (HIWORD(pBar) == 0) continue; // placeholder
    if (!pBar->IsVisible()) continue;
    BOOL bIsSizingBar =
    pBar->IsKindOf(RUNTIME_CLASS(CSizingControlBar));

    int nLengthBar; // minimum length of the bar
    if (bIsSizingBar)
    nLengthBar = bHorz ? pBar->m_szMinHorz.cx - 2 :
    pBar->m_szMinVert.cy - 2;
    else
    {
    CRect rcBar;
    pBar->GetWindowRect(&rcBar);
    nLengthBar = bHorz ? rcBar.Width() - 2 : rcBar.Height() - 2;
    }

    nLengthMin += nLengthBar;
    if (nLengthMin > nLengthTotal)
    {
    // split the row after fixed bar
    if (i < nThis)
    {
    m_pDockBar->m_arrBars.InsertAt(i + 1,
    (CControlBar*) NULL);
    return FALSE;
    }

    // only this sizebar remains on the row, adjust it to minsize
    if (i == nThis)
    {
    if (bHorz)
    m_szHorz.cx = m_szMinHorz.cx;
    else
    m_szVert.cy = m_szMinVert.cy;

    return TRUE; // the dockbar will split the row for us
    }

    // we have enough bars - go negotiate with them
    m_pDockBar->m_arrBars.InsertAt(i, (CControlBar*) NULL);
    nLast = i - 1;
    break;
    }

    if (bIsSizingBar)
    {
    nLengthActual += bHorz ? pBar->m_szHorz.cx - 2 :
    pBar->m_szVert.cy - 2;
    nWidthMax = max(nWidthMax, bHorz ? pBar->m_szHorz.cy :
    pBar->m_szVert.cx);
    }
    else
    nLengthAvail -= nLengthBar;
    }

    CSCBArray arrSCBars;
    GetRowSizingBars(arrSCBars);
    int nNumBars = arrSCBars.GetSize();
    int nDelta = nLengthAvail - nLengthActual;

    // return faster when there is only one sizing bar per row (this one)
    if (nNumBars == 1)
    {
    ASSERT(arrSCBars[0] == this);

    if (nDelta == 0)
    return TRUE;

    m_bKeepSize = FALSE;
    (bHorz ? m_szHorz.cx : m_szVert.cy) += nDelta;

    return TRUE;
    }

    // make all the bars the same width
    for (i = 0; i < nNumBars; i++)
    if (bHorz)
    arrSCBars[i]->m_szHorz.cy = nWidthMax;
    else
    arrSCBars[i]->m_szVert.cx = nWidthMax;

    // distribute the difference between the bars,
    // but don't shrink them below their minsizes
    while (nDelta != 0)
    {
    int nDeltaOld = nDelta;
    for (i = 0; i < nNumBars; i++)
    {
    pBar = arrSCBars[i];
    int nLMin = bHorz ?
    pBar->m_szMinHorz.cx : pBar->m_szMinVert.cy;
    int nL = bHorz ? pBar->m_szHorz.cx : pBar->m_szVert.cy;

    if ((nL == nLMin) && (nDelta < 0) || // already at min length
    pBar->m_bKeepSize) // or wants to keep its size
    continue;

    // sign of nDelta
    int nDelta2 = (nDelta == 0) ? 0 : ((nDelta < 0) ? -1 : 1);

    (bHorz ? pBar->m_szHorz.cx : pBar->m_szVert.cy) += nDelta2;
    nDelta -= nDelta2;
    if (nDelta == 0) break;
    }
    // clear m_bKeepSize flags
    if ((nDeltaOld == nDelta) || (nDelta == 0))
    for (i = 0; i < nNumBars; i++)
    arrSCBars[i]->m_bKeepSize = FALSE;
    }

    return TRUE;
    }

    void CSizingControlBar::AlignControlBars()
    {
    int nFirst, nLast, nThis;
    GetRowInfo(nFirst, nLast, nThis);

    BOOL bHorz = IsHorzDocked();
    BOOL bNeedRecalc = FALSE;
    int nAlign = bHorz ? -2 : 0;

    CRect rc, rcDock;
    m_pDockBar->GetWindowRect(&rcDock);

    for (int i = nFirst; i <= nLast; i++)
    {
    CSizingControlBar* pBar =
    (CSizingControlBar*) m_pDockBar->m_arrBars[i];
    if (HIWORD(pBar) == 0) continue; // placeholder
    if (!pBar->IsVisible()) continue;

    pBar->GetWindowRect(&rc);
    rc.OffsetRect(-rcDock.TopLeft());

    if (pBar->IsKindOf(RUNTIME_CLASS(CSizingControlBar)))
    rc = CRect(rc.TopLeft(),
    bHorz ? pBar->m_szHorz : pBar->m_szVert);

    if ((bHorz ? rc.left : rc.top) != nAlign)
    {
    if (!bHorz)
    rc.OffsetRect(0, nAlign - rc.top - 2);
    else if (m_nDockBarID == AFX_IDW_DOCKBAR_TOP)
    rc.OffsetRect(nAlign - rc.left, -2);
    else
    rc.OffsetRect(nAlign - rc.left, 0);
    pBar->MoveWindow(rc);
    bNeedRecalc = TRUE;
    }
    nAlign += (bHorz ? rc.Width() : rc.Height()) - 2;
    }

    if (bNeedRecalc)
    m_pDockSite->DelayRecalcLayout();
    }

    void CSizingControlBar::OnUpdateCmdUI(CFrameWnd* pTarget,
    BOOL bDisableIfNoHndler)
    {
    UNUSED_ALWAYS(bDisableIfNoHndler);
    UNUSED_ALWAYS(pTarget);
    }

    void CSizingControlBar::LoadState(LPCTSTR lpszProfileName)
    {
    ASSERT_VALID(this);
    ASSERT(GetSafeHwnd()); // must be called after Create()

    #if defined(_SCB_REPLACE_MINIFRAME) && !defined(_SCB_MINIFRAME_CAPTION)
    // compensate the caption miscalculation in CFrameWnd::SetDockState()
    CDockState state;
    state.LoadState(lpszProfileName);

    UINT nID = GetDlgCtrlID();
    for (int i = 0; i < state.m_arrBarInfo.GetSize(); i++)
    {
    CControlBarInfo* pInfo = (CControlBarInfo*)state.m_arrBarInfo[i];
    ASSERT(pInfo != NULL);
    if (!pInfo->m_bFloating)
    continue;

    // this is a floating dockbar - check the ID array
    for (int j = 0; j < pInfo->m_arrBarID.GetSize(); j++)
    if ((DWORD) pInfo->m_arrBarID[j] == nID)
    {
    // found this bar - offset origin and save settings
    pInfo->m_pointPos.x++;
    pInfo->m_pointPos.y +=
    ::GetSystemMetrics(SM_CYSMCAPTION) + 1;
    pInfo->SaveState(lpszProfileName, i);
    }
    }
    #endif //_SCB_REPLACE_MINIFRAME && !_SCB_MINIFRAME_CAPTION

    CWinApp* pApp = AfxGetApp();

    TCHAR szSection[256];
    wsprintf(szSection, _T("%s-SCBar-%d"), lpszProfileName,
    GetDlgCtrlID());

    m_szHorz.cx = max(m_szMinHorz.cx, (int) pApp->GetProfileInt(
    szSection, _T("sizeHorzCX"), m_szHorz.cx));
    m_szHorz.cy = max(m_szMinHorz.cy, (int) pApp->GetProfileInt(
    szSection, _T("sizeHorzCY"), m_szHorz.cy));

    m_szVert.cx = max(m_szMinVert.cx, (int) pApp->GetProfileInt(
    szSection, _T("sizeVertCX"), m_szVert.cx));
    m_szVert.cy = max(m_szMinVert.cy, (int) pApp->GetProfileInt(
    szSection, _T("sizeVertCY"), m_szVert.cy));

    m_szFloat.cx = max(m_szMinFloat.cx, (int) pApp->GetProfileInt(
    szSection, _T("sizeFloatCX"), m_szFloat.cx));
    m_szFloat.cy = max(m_szMinFloat.cy, (int) pApp->GetProfileInt(
    szSection, _T("sizeFloatCY"), m_szFloat.cy));
    }

    void CSizingControlBar::SaveState(LPCTSTR lpszProfileName)
    {
    // place your SaveState or GlobalSaveState call in
    // CMainFrame's OnClose() or DestroyWindow(), not in OnDestroy()
    ASSERT_VALID(this);
    ASSERT(GetSafeHwnd());

    CWinApp* pApp = AfxGetApp();

    TCHAR szSection[256];
    wsprintf(szSection, _T("%s-SCBar-%d"), lpszProfileName,
    GetDlgCtrlID());

    pApp->WriteProfileInt(szSection, _T("sizeHorzCX"), m_szHorz.cx);
    pApp->WriteProfileInt(szSection, _T("sizeHorzCY"), m_szHorz.cy);

    pApp->WriteProfileInt(szSection, _T("sizeVertCX"), m_szVert.cx);
    pApp->WriteProfileInt(szSection, _T("sizeVertCY"), m_szVert.cy);

    pApp->WriteProfileInt(szSection, _T("sizeFloatCX"), m_szFloat.cx);
    pApp->WriteProfileInt(szSection, _T("sizeFloatCY"), m_szFloat.cy);
    }

    void CSizingControlBar::GlobalLoadState(CFrameWnd* pFrame,
    LPCTSTR lpszProfileName)
    {
    POSITION pos = pFrame->m_listControlBars.GetHeadPosition();
    while (pos != NULL)
    {
    CSizingControlBar* pBar =
    (CSizingControlBar*) pFrame->m_listControlBars.GetNext(pos);
    ASSERT(pBar != NULL);
    if (pBar->IsKindOf(RUNTIME_CLASS(CSizingControlBar)))
    pBar->LoadState(lpszProfileName);
    }
    }

    void CSizingControlBar::GlobalSaveState(CFrameWnd* pFrame,
    LPCTSTR lpszProfileName)
    {
    POSITION pos = pFrame->m_listControlBars.GetHeadPosition();
    while (pos != NULL)
    {
    CSizingControlBar* pBar =
    (CSizingControlBar*) pFrame->m_listControlBars.GetNext(pos);
    ASSERT(pBar != NULL);
    if (pBar->IsKindOf(RUNTIME_CLASS(CSizingControlBar)))
    pBar->SaveState(lpszProfileName);
    }
    }

    #ifdef _SCB_REPLACE_MINIFRAME
    #ifndef _SCB_MINIFRAME_CAPTION
    /////////////////////////////////////////////////////////////////////////////
    // CSCBDockContext Drag Operations

    static void AdjustRectangle(CRect& rect, CPoint pt)
    {
    int nXOffset = (pt.x < rect.left) ? (pt.x - rect.left) :
    (pt.x > rect.right) ? (pt.x - rect.right) : 0;
    int nYOffset = (pt.y < rect.top) ? (pt.y - rect.top) :
    (pt.y > rect.bottom) ? (pt.y - rect.bottom) : 0;
    rect.OffsetRect(nXOffset, nYOffset);
    }

    void CSCBDockContext::StartDrag(CPoint pt)
    {
    ASSERT_VALID(m_pBar);
    m_bDragging = TRUE;

    InitLoop();

    ASSERT((m_pBar->m_dwStyle & CBRS_SIZE_DYNAMIC) != 0);

    // get true bar size (including borders)
    CRect rect;
    m_pBar->GetWindowRect(rect);
    m_ptLast = pt;
    CSize sizeHorz = m_pBar->CalcDynamicLayout(0, LM_HORZ | LM_HORZDOCK);
    CSize sizeVert = m_pBar->CalcDynamicLayout(0, LM_VERTDOCK);
    CSize sizeFloat = m_pBar->CalcDynamicLayout(0, LM_HORZ | LM_MRUWIDTH);

    m_rectDragHorz = CRect(rect.TopLeft(), sizeHorz);
    m_rectDragVert = CRect(rect.TopLeft(), sizeVert);

    // calculate frame dragging rectangle
    m_rectFrameDragHorz = CRect(rect.TopLeft(), sizeFloat);

    #ifdef _MAC
    CMiniFrameWnd::CalcBorders(&m_rectFrameDragHorz,
    WS_THICKFRAME, WS_EX_FORCESIZEBOX);
    #else
    CMiniFrameWnd::CalcBorders(&m_rectFrameDragHorz, WS_THICKFRAME);
    #endif
    m_rectFrameDragHorz.DeflateRect(2, 2);
    m_rectFrameDragVert = m_rectFrameDragHorz;

    // adjust rectangles so that point is inside
    AdjustRectangle(m_rectDragHorz, pt);
    AdjustRectangle(m_rectDragVert, pt);
    AdjustRectangle(m_rectFrameDragHorz, pt);
    AdjustRectangle(m_rectFrameDragVert, pt);

    // initialize tracking state and enter tracking loop
    m_dwOverDockStyle = CanDock();
    Move(pt); // call it here to handle special keys
    Track();
    }
    #endif //_SCB_MINIFRAME_CAPTION

    /////////////////////////////////////////////////////////////////////////////
    // CSCBMiniDockFrameWnd

    IMPLEMENT_DYNCREATE(CSCBMiniDockFrameWnd, baseCSCBMiniDockFrameWnd);

    BEGIN_MESSAGE_MAP(CSCBMiniDockFrameWnd, baseCSCBMiniDockFrameWnd)
    //{{AFX_MSG_MAP(CSCBMiniDockFrameWnd)
    ON_WM_NCLBUTTONDOWN()
    ON_WM_GETMINMAXINFO()
    ON_WM_WINDOWPOSCHANGING()
    ON_WM_SIZE()
    //}}AFX_MSG_MAP
    END_MESSAGE_MAP()

    BOOL CSCBMiniDockFrameWnd::Create(CWnd* pParent, DWORD dwBarStyle)
    {
    // set m_bInRecalcLayout to avoid flashing during creation
    // RecalcLayout will be called once something is docked
    m_bInRecalcLayout = TRUE;

    DWORD dwStyle = WS_POPUP|WS_CAPTION|WS_SYSMENU|MFS_MOVEFRAME|
    MFS_4THICKFRAME|MFS_SYNCACTIVE|MFS_BLOCKSYSMENU|
    FWS_SNAPTOBARS;

    if (dwBarStyle & CBRS_SIZE_DYNAMIC)
    dwStyle &= ~MFS_MOVEFRAME;

    DWORD dwExStyle = 0;
    #ifdef _MAC
    if (dwBarStyle & CBRS_SIZE_DYNAMIC)
    dwExStyle |= WS_EX_FORCESIZEBOX;
    else
    dwStyle &= ~(MFS_MOVEFRAME|MFS_4THICKFRAME);
    #endif

    if (!CMiniFrameWnd::CreateEx(dwExStyle,
    NULL, &afxChNil, dwStyle, rectDefault, pParent))
    {
    m_bInRecalcLayout = FALSE;
    return FALSE;
    }
    dwStyle = dwBarStyle & (CBRS_ALIGN_LEFT|CBRS_ALIGN_RIGHT) ?
    CBRS_ALIGN_LEFT : CBRS_ALIGN_TOP;
    dwStyle |= dwBarStyle & CBRS_FLOAT_MULTI;
    CMenu* pSysMenu = GetSystemMenu(FALSE);
    //pSysMenu->DeleteMenu(SC_SIZE, MF_BYCOMMAND);
    CString strHide;
    if (strHide.LoadString(AFX_IDS_HIDE))
    {
    pSysMenu->DeleteMenu(SC_CLOSE, MF_BYCOMMAND);
    pSysMenu->AppendMenu(MF_STRING|MF_ENABLED, SC_CLOSE, strHide);
    }

    // must initially create with parent frame as parent
    if (!m_wndDockBar.Create(pParent, WS_CHILD | WS_VISIBLE | dwStyle,
    AFX_IDW_DOCKBAR_FLOAT))
    {
    m_bInRecalcLayout = FALSE;
    return FALSE;
    }

    // set parent to CMiniDockFrameWnd
    m_wndDockBar.SetParent(this);
    m_bInRecalcLayout = FALSE;

    return TRUE;
    }

    void CSCBMiniDockFrameWnd::OnNcLButtonDown(UINT nHitTest, CPoint point)
    {
    if (nHitTest == HTCAPTION || nHitTest == HTCLOSE)
    {
    baseCSCBMiniDockFrameWnd::OnNcLButtonDown(nHitTest, point);
    return;
    }

    if (GetSizingControlBar() != NULL)
    CMiniFrameWnd::OnNcLButtonDown(nHitTest, point);
    else
    baseCSCBMiniDockFrameWnd::OnNcLButtonDown(nHitTest, point);
    }

    CSizingControlBar* CSCBMiniDockFrameWnd::GetSizingControlBar()
    {
    CWnd* pWnd = GetWindow(GW_CHILD); // get the dockbar
    if (pWnd == NULL)
    return NULL;

    pWnd = pWnd->GetWindow(GW_CHILD); // get the controlbar
    if (pWnd == NULL)
    return NULL;

    if (!pWnd->IsKindOf(RUNTIME_CLASS(CSizingControlBar)))
    return NULL;

    return (CSizingControlBar*) pWnd;
    }

    void CSCBMiniDockFrameWnd::OnSize(UINT nType, int cx, int cy)
    {
    CSizingControlBar* pBar = GetSizingControlBar();
    if ((pBar != NULL) && (GetStyle() & MFS_4THICKFRAME) == 0
    && pBar->IsVisible())
    pBar->m_szFloat = CSize(cx + 4, cy + 4);

    baseCSCBMiniDockFrameWnd::OnSize(nType, cx, cy);
    }

    void CSCBMiniDockFrameWnd::OnGetMinMaxInfo(MINMAXINFO FAR* lpMMI)
    {
    baseCSCBMiniDockFrameWnd::OnGetMinMaxInfo(lpMMI);

    CSizingControlBar* pBar = GetSizingControlBar();
    if (pBar != NULL)
    {
    CRect r(CPoint(0, 0), pBar->m_szMinFloat - CSize(4, 4));
    #ifndef _SCB_MINIFRAME_CAPTION
    CMiniFrameWnd::CalcBorders(&r, WS_THICKFRAME);
    #else
    CMiniFrameWnd::CalcBorders(&r, WS_THICKFRAME|WS_CAPTION);
    #endif //_SCB_MINIFRAME_CAPTION
    lpMMI->ptMinTrackSize.x = r.Width();
    lpMMI->ptMinTrackSize.y = r.Height();
    }
    }

    void CSCBMiniDockFrameWnd::OnWindowPosChanging(WINDOWPOS FAR* lpwndpos)
    {
    if ((GetStyle() & MFS_4THICKFRAME) != 0)
    {
    CSizingControlBar* pBar = GetSizingControlBar();
    if (pBar != NULL)
    {
    lpwndpos->flags |= SWP_NOSIZE; // don't size this time
    // prevents flicker
    pBar->m_pDockBar->ModifyStyle(0, WS_CLIPCHILDREN);
    // enable diagonal resizing
    ModifyStyle(MFS_4THICKFRAME, 0);
    #ifndef _SCB_MINIFRAME_CAPTION
    // remove caption
    ModifyStyle(WS_SYSMENU|WS_CAPTION, 0);
    #endif
    DelayRecalcLayout();
    pBar->PostMessage(WM_NCPAINT);
    }
    }

    CMiniFrameWnd::OnWindowPosChanging(lpwndpos);
    }

    #endif //_SCB_REPLACE_MINIFRAME

  • 相关阅读:
    JavaScript -- 条件语句和循环语句
    xpath的|
    Pythonic
    4k图片爬取+中文乱码
    xpath-房价爬取
    (.*?)实验室
    模块的循环导入
    bs4-爬取小说
    糗图-图片爬取
    re实战记录
  • 原文地址:https://www.cnblogs.com/yangzizhen/p/4106063.html
Copyright © 2011-2022 走看看