📄 explorertoolbarctrl.h
字号:
#pragma once
// for debug
#ifdef _DEBUG
const bool _Mtl_ExplorerToolBarCtrl_traceOn = false;
#define etbTRACE if (_Mtl_ExplorerToolBarCtrl_traceOn) ATLTRACE
#else
#define etbTRACE
#endif
template <class _ExpBar>
class CExpBarMenu : public CFavoritesMenu<CExpBarMenu>
{
public:
_ExpBar* __m_pExpBar;
CExpBarMenu(_ExpBar* __pExpBar, int nInsertPointMenuItemID)
: CFavoritesMenu<CExpBarMenu>(nInsertPointMenuItemID, _T("(empty)"),
0x012c, 0x7530, _T("Open All")),
__m_pExpBar(__pExpBar)
{
RefreshStyle();
}
// Overrides
void OnExecute(const CString& strFilePath)
{
__m_pExpBar->OnExecuteFromExpMenu(strFilePath);
}
void RefreshStyle()
{
SetStyle(CFavoritesMenuOption::GetStyle());
m_nMaxMenuItemTextLength = CFavoritesMenuOption::GetMaxMenuItemTextLength();
m_nMaxMenuBreakCount = CFavoritesMenuOption::GetMaxMenuBreakCount();
}
};
template <class T, class TBase = CToolBarCtrl, class TWinTraits = CControlWinTraits>
class ATL_NO_VTABLE CExplorerToolBarCtrlImpl :
public CWindowImpl< T, TBase, TWinTraits>,
public CFileNotification
{
public:
// Declarations
DECLARE_WND_SUPERCLASS(NULL, TBase::GetWndClassName())
typedef CExplorerToolBarCtrlImpl<T, TBase, TWinTraits> thisClass;
// Constants
enum { s_nIDLast = 100 };
// Data members
CFont m_font;
CContainedWindow m_wndParent;
CMenu m_menu;
CExpBarMenu<CExplorerToolBarCtrlImpl> m_ExpMenu;
CItemIDList m_idlRootFolder; // root idl
CCrasyMap<int, CItemIDList> m_mapID; // command id and idlist
CSimpleArray<int> m_arrFolderCmdID; // folders
CItemIDList m_idlHtml; // for faster drawing
int m_nMaxID, m_nMinID, m_nCurrentID;
CComPtr<IContextMenu2> m_spContextMenu2;
// Constructor
CExplorerToolBarCtrlImpl(int nInsertPointMenuItemID, int nMinID, int nMaxID) :
m_wndParent(this, 1), m_ExpMenu(this, nInsertPointMenuItemID),
m_nMaxID(nMaxID), m_nMinID(nMinID)
{
m_menu.CreatePopupMenu();
m_menu.InsertMenu(0, MF_BYPOSITION | MF_STRING, nInsertPointMenuItemID, _T("InsertPoint"));
m_ExpMenu.InstallExplorerMenu(m_menu.m_hMenu);
m_nCurrentID = m_nMinID;
m_idlHtml = MtlGetHtmlFileIDList();
}
~CExplorerToolBarCtrlImpl()
{
if (m_wndParent.IsWindow())
m_wndParent.UnsubclassWindow();
}
// Attributes
void SetExplorerToolBarRootPath(const CString& strPath)
{
m_idlRootFolder = strPath;
}
CString GetExplorerToolBarRootPath()
{
return m_idlRootFolder.GetPath();
}
// Overridables
void OnInitExplorerToolBarCtrl()
{
}
void OnTermExplorerToolBarCtrl()
{
}
void OnExecute(const CString& strPath)
{
}
void OnInitialUpdateTBButtons(CSimpleArray<TBBUTTON>& btns, LPCITEMIDLIST pidl)
{
std::sort(_begin(btns), _end(btns), _DefaultTBBtnCompare<thisClass>(this));
}
bool OnRenameExplorerToolBarCtrl(CString& strName)
{
return false;
}
// Methods
void SetRootDirectoryPath(const CString& strPath)
{
m_strRootPath = strPath;
}
void OnExecuteFromExpMenu(const CString& strPath)
{
T* pT = static_cast<T*>(this);
pT->OnExecute(strPath);
}
// Message map and handlers
BEGIN_MSG_MAP(CExplorerToolBarCtrlImpl)
MESSAGE_HANDLER(WM_CREATE, OnCreate)
MESSAGE_HANDLER(WM_DESTROY, OnDestroy)
HANDLE_MENU_MESSAGE_CONTEXTMENU(m_spContextMenu2)
MESSAGE_HANDLER(WM_RBUTTONUP, OnRButtonUp)
MESSAGE_HANDLER(GET_REGISTERED_MESSAGE(Mtl_FileNotification), OnFileNotification)
CHAIN_MSG_MAP_MEMBER(m_ExpMenu)
// REFLECTED_NOTIFY_CODE_HANDLER(TBN_DROPDOWN, OnDropDown)
ALT_MSG_MAP(1)
NOTIFY_CODE_HANDLER(RBN_CHEVRONPUSHED, OnChevronPushed)
NOTIFY_CODE_HANDLER(TTN_GETDISPINFO, OnToolTipText)
COMMAND_RANGE_HANDLER_EX(m_nMinID, m_nMaxID, OnCommandRange)
END_MSG_MAP()
LRESULT OnToolTipText(int idCtrl, LPNMHDR pnmh, BOOL& bHandled)
{
LPNMTTDISPINFO pDispInfo = (LPNMTTDISPINFO)pnmh;
pDispInfo->szText[0] = 0;
bHandled = FALSE;
if((idCtrl != 0) && !(pDispInfo->uFlags & TTF_IDISHWND) &&
m_nMinID <= idCtrl && idCtrl <= m_nMaxID)
{
CItemIDList idlFolder = m_idlRootFolder;
CItemIDList idl = m_mapID.Lookup(idCtrl);
CString strPath = idl.GetPath();
idl -= idlFolder;
if (idl.IsNull())
return 0;
int nLen = _countof(pDispInfo->szText);
CString strName = MtlGetDisplayName(idl);
CString strUrl = MtlGetInternetShortcutUrl(strPath);
CString strTip = MtlMakeFavoriteToolTipText(strName, strUrl, nLen);
::lstrcpyn(pDispInfo->szText, strTip, nLen);
bHandled = TRUE;
}
return 0;
}
LRESULT OnFileNotification(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& /*bHandled*/)
{
_UpdateButtons();// sorry
MtlRefreshBandIdealSize(GetParent(), m_hWnd);
return 0;
}
LRESULT OnRButtonUp(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& /*bHandled*/)
{
CPoint pt(GET_X_LPARAM(lParam), GET_Y_LPARAM(lParam));
int nIndex = HitTest(&pt);
if (nIndex < 0)
return 0;
TBBUTTON tbb;
GetButton(nIndex, &tbb);
int nCmdID = tbb.idCommand;
MarkButton(nCmdID, TRUE);
_PopupContextMenu(nCmdID, pt);
MarkButton(nCmdID, FALSE);
return 0;
}
LRESULT OnChevronPushed(int /*idCtrl*/, LPNMHDR pnmh, BOOL& bHandled)
{
LPNMREBARCHEVRON lpnm = (LPNMREBARCHEVRON)pnmh;
if (lpnm->wID != GetDlgCtrlID()) {
bHandled = FALSE;
return 1;
}
CWindow wnd(m_hWnd);
int nCount = (int)wnd.SendMessage(TB_BUTTONCOUNT);
if (nCount <= 0) // probably not a toolbar
return 1;
RECT rcClient;
BOOL bRet = wnd.GetClientRect(&rcClient);
ATLASSERT(bRet);
for(int i = 0; i < nCount; i++)
{
TBBUTTON tbb;
bRet = (BOOL)wnd.SendMessage(TB_GETBUTTON, i, (LPARAM)&tbb);
ATLASSERT(bRet);
RECT rcButton;
bRet = (BOOL)wnd.SendMessage(TB_GETITEMRECT, i, (LPARAM)&rcButton);
ATLASSERT(bRet);
if(!(rcButton.right > rcClient.right))
{
CString strPath = _GetPathFromCmdID(tbb.idCommand);
ATLASSERT(!strPath.IsEmpty());
m_ExpMenu.AddIgnoredPath(strPath);
}
}
CWindow wndFrom = lpnm->hdr.hwndFrom;
RECT rect = lpnm->rc;
wndFrom.ClientToScreen(&rect);
TPMPARAMS TPMParams;
TPMParams.cbSize = sizeof(TPMPARAMS);
TPMParams.rcExclude = rect;
m_ExpMenu.SetRootDirectoryPath(m_idlRootFolder.GetPath());
DoTrackPopupMenu(m_menu.m_hMenu, TPM_LEFTBUTTON | TPM_RIGHTBUTTON | TPM_VERTICAL | TPM_LEFTALIGN | TPM_TOPALIGN |
(!AtlIsOldWindows() ? (true ? TPM_VERPOSANIMATION : TPM_NOANIMATION) : 0), rect.left, rect.bottom, &TPMParams);
// eat next message if click is on the same button
MtlEatNextLButtonDownOnChevron(GetTopLevelParent(), rect);
m_ExpMenu.ResetIgnoredPath();
return 0;
}
void OnCommandRange(UINT, int nID, HWND hWndCtrl)
{
etbTRACE(_T("CExplorerMenu::OnCommandRange : %d\n"), nID);
// if (hWndCtrl != m_hWnd) {// removed for chevron
// ATLTRACE2(atlTraceUser, 4, " It's not mine");
// SetMsgHandled(FALSE);
// return;
// }
DoPopupMenu(nID, true);
}
LRESULT OnCreate(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& /*bHandled*/)
{
// These styles are required
ModifyStyle(0, TBSTYLE_LIST | TBSTYLE_FLAT);
// Let the toolbar initialize itself
LRESULT lRet = DefWindowProc(uMsg, wParam, lParam);
// get and use system settings
_GetSystemSettings();
// set image list
_SetSystemImageList();
// Parent init
CWindow wndParent = GetParent();
CWindow wndTopLevelParent = wndParent.GetTopLevelParent();
m_wndParent.SubclassWindow(wndTopLevelParent);
// Toolbar Init
SetButtonStructSize();
_UpdateButtons();
SetUpFileNotificationThread(m_hWnd, m_idlRootFolder.GetPath(), false);
CFavoritesMenuOption::Add(m_hWnd);
T* pT = static_cast<T*>(this);
pT->OnInitExplorerToolBarCtrl();
return lRet;
}
LRESULT OnDestroy(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled)
{
bHandled = FALSE;
T* pT = static_cast<T*>(this);
pT->OnTermExplorerToolBarCtrl();
return 0;
}
LRESULT OnDropDown(int idCtrl, LPNMHDR pnmh, BOOL& bHandled)
{
// Check if this comes from us
if(pnmh->hwndFrom != m_hWnd)
{
bHandled = FALSE;
return 1;
}
LPNMTOOLBAR pNMToolBar = (LPNMTOOLBAR)pnmh;
int nCmdID = pNMToolBar->iItem;
DoPopupMenu(nCmdID, true);
return TBDDRET_TREATPRESSED;
}
/* CString _CommandToPath(int nID)
{
return m_mapID[nID];
}
*/
void _GetSystemSettings()
{
// refresh our font
NONCLIENTMETRICS info;
info.cbSize = sizeof(info);
::SystemParametersInfo(SPI_GETNONCLIENTMETRICS, sizeof(info), &info, 0);
CLogFont logfont;
logfont.InitDefault();
if(m_font.m_hFont != NULL)
m_font.GetLogFont(logfont);
if(logfont != info.lfMenuFont)
{
HFONT hFontMenu = ::CreateFontIndirect(&info.lfMenuFont);
ATLASSERT(hFontMenu != NULL);
if(hFontMenu != NULL)
{
if(m_font.m_hFont != NULL)
m_font.DeleteObject();
m_font.Attach(hFontMenu);
SetFont(m_font);
AddStrings(_T("NS\0")); // for proper item height
AutoSize();
}
}
}
void _CleanUpButtons()
{
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -