⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 favtreeviewctrl.h

📁 一个使用wtl写的完整的多窗口浏览器
💻 H
📖 第 1 页 / 共 2 页
字号:
		CHAIN_MSG_MAP(CChevronHandler<CDonutFavoritesBarImpl>)
		CHAIN_MSG_MAP(CUpdateCmdUI<CDonutFavoritesBarImpl>)
		FORWARD_NOTIFICATIONS()
	END_MSG_MAP()

	LRESULT OnFavTreeStandard(WORD /*wNotifyCode*/, WORD /*wID*/, HWND /*hWndCtl*/, BOOL& /*bHandled*/)
	{
		m_view.ModifyExplorerTreeViewExtendedStyle(ETV_EX_FOLDERS, ETV_EX_FAVORITES);

		m_wndToolBar.UpdateWindow();
		m_view.RefreshRootTree();

		return 0;
	}
	LRESULT OnFavTreeGroup(WORD /*wNotifyCode*/, WORD /*wID*/, HWND /*hWndCtl*/, BOOL& /*bHandled*/)
	{
		m_view.ModifyExplorerTreeViewExtendedStyle(ETV_EX_FOLDERS, ETV_EX_FAVORITEGROUP);
		
		m_wndToolBar.UpdateWindow();
		m_view.RefreshRootTree();

		return 0;
	}
	LRESULT OnFavTreeUser(WORD /*wNotifyCode*/, WORD /*wID*/, HWND /*hWndCtl*/, BOOL& /*bHandled*/)
	{
		m_view.ModifyExplorerTreeViewExtendedStyle(ETV_EX_FOLDERS, ETV_EX_USERDEFINED);

		m_wndToolBar.UpdateWindow();
		m_view.RefreshRootTree();

		return 0;
	}
	LRESULT OnFavTreeMyComputer(WORD /*wNotifyCode*/, WORD /*wID*/, HWND /*hWndCtl*/, BOOL& /*bHandled*/)
	{
		m_view.ModifyExplorerTreeViewExtendedStyle(ETV_EX_FOLDERS, ETV_EX_MYCOMPUTER);

		m_wndToolBar.UpdateWindow();
		m_view.RefreshRootTree();

		return 0;
	}
	LRESULT OnFavTreeShellExecute(WORD /*wNotifyCode*/, WORD /*wID*/, HWND /*hWndCtl*/, BOOL& /*bHandled*/)
	{
		if (_check_flag(ETV_EX_SHELLEXECUTE, m_view.GetExplorerTreeViewExtendedStyle()))
			m_view.ModifyExplorerTreeViewExtendedStyle(ETV_EX_SHELLEXECUTE, 0);
		else
			m_view.ModifyExplorerTreeViewExtendedStyle(0, ETV_EX_SHELLEXECUTE);

		return 0;
	}
	LRESULT OnFavTreeLoadRemoteIcon(WORD /*wNotifyCode*/, WORD /*wID*/, HWND /*hWndCtl*/, BOOL& /*bHandled*/)
	{
		if (_check_flag(ETV_EX_LOADREMOTEICON, m_view.GetExplorerTreeViewExtendedStyle()))
			m_view.ModifyExplorerTreeViewExtendedStyle(ETV_EX_LOADREMOTEICON, 0);
		else
			m_view.ModifyExplorerTreeViewExtendedStyle(0, ETV_EX_LOADREMOTEICON);

		m_wndToolBar.UpdateWindow();
		m_view.RefreshRootTree();

		return 0;
	}
	LRESULT OnFavoritePlacement(WORD /*wNotifyCode*/, WORD /*wID*/, HWND /*hWndCtl*/, BOOL& /*bHandled*/)
	{
		m_wndToolBar.UpdateWindow();
		m_view.RefreshRootTree();
		return 0;
	}
	LRESULT OnFavTreeSingleExpand(WORD /*wNotifyCode*/, WORD /*wID*/, HWND /*hWndCtl*/, BOOL& /*bHandled*/)
	{
		if (_check_flag(ETV_EX_SINGLEEXPAND, m_view.GetExplorerTreeViewExtendedStyle()))
			m_view.ModifyExplorerTreeViewExtendedStyle(ETV_EX_SINGLEEXPAND, 0);
		else
			m_view.ModifyExplorerTreeViewExtendedStyle(0, ETV_EX_SINGLEEXPAND);

		m_wndToolBar.UpdateWindow();
		m_view.RefreshRootTree();

		return 0;
	}

	LRESULT OnTbnDropDown(int /*idCtrl*/, LPNMHDR pnmh, BOOL& bHandled)
	{
		LPNMTOOLBAR lpnmtb = (LPNMTOOLBAR)pnmh;

		CRect rc; m_wndToolBar.GetItemRect(0, &rc);
		ClientToScreen(&rc);
		UINT uMenuFlags = TPM_LEFTBUTTON | TPM_RIGHTBUTTON | TPM_VERTICAL | TPM_LEFTALIGN | TPM_TOPALIGN | (!AtlIsOldWindows() ? TPM_VERPOSANIMATION : 0);
		TPMPARAMS TPMParams;
		TPMParams.cbSize = sizeof(TPMPARAMS);
		TPMParams.rcExclude = rc;

		::TrackPopupMenuEx(m_menuPlacement.GetSubMenu(0), uMenuFlags, rc.left + 1, rc.bottom + 2, m_hWnd, &TPMParams);

		return TBDDRET_DEFAULT;
	}

	LRESULT OnPaint(UINT /*uMsg*/, WPARAM /*wParam*/, LPARAM /*lParam*/, BOOL& /*bHandled*/)
	{
		CPaintDC dc(m_hWnd);

		T* pT = static_cast<T*>(this);
		pT->DrawPaneTitle(dc.m_hDC);

		return 0;
	}

	LRESULT OnEraseBackground(UINT /*uMsg*/, WPARAM wParam, LPARAM /*lParam*/, BOOL& /*bHandled*/)
	{
		return 1;	// no background needed
	}

	LRESULT OnDestroy(UINT /*uMsg*/, WPARAM /*wParam*/, LPARAM /*lParam*/, BOOL& bHandled)
	{
		bHandled = FALSE;
		MtlDestroyImageLists(m_hWnd);
		return 0;
	}

	LRESULT OnCreate(UINT /*uMsg*/, WPARAM /*wParam*/, LPARAM /*lParam*/, BOOL& /*bHandled*/)
	{
		m_view.Create(m_hWnd, rcDefault, NULL, WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_CLIPCHILDREN |
			TVS_INFOTIP | TVS_EDITLABELS | TVS_SHOWSELALWAYS | TVS_SINGLEEXPAND | TVS_FULLROWSELECT | TVS_TRACKSELECT, 0);//WS_EX_STATICEDGE);

		m_wndReBar = _CreateSimpleReBarCtrl(m_hWnd, ATL_SIMPLE_REBAR_NOBORDER_STYLE|CCS_NOPARENTALIGN);

		CFavoritesMenuOption::Add(m_hWnd);

		return 0;
	}

	LRESULT OnSize(UINT /*uMsg*/, WPARAM /*wParam*/, LPARAM lParam, BOOL& /*bHandled*/)
	{
		UpdateLayout(GET_X_LPARAM(lParam), GET_Y_LPARAM(lParam));
		return 0;
	}

	LRESULT OnSetFocus(UINT /*uMsg*/, WPARAM /*wParam*/, LPARAM /*lParam*/, BOOL& /*bHandled*/)
	{
		if(m_view.m_hWnd != NULL)
			m_view.SetFocus();
		return 0;
	}

	void InitToolBar(int nIDAdd, int nIDOrganize, int nIDSpecial,
					 UINT nImageBmpID, UINT nHotImageBmpID, 
					 int cx, int cy, COLORREF clrMask, UINT nFlags = ILC_COLOR8)
	{
		CImageList imgs;
		MTLVERIFY(imgs.Create(cx, cy, nFlags | ILC_MASK, 1, 1));

		CBitmap bmp;
		MTLVERIFY(bmp.LoadBitmap(nImageBmpID));
		imgs.Add(bmp, clrMask);

		CImageList imgsHot;
		MTLVERIFY(imgsHot.Create(cx, cy, nFlags | ILC_MASK, 1, 1));

		CBitmap bmpHot;
		MTLVERIFY(bmpHot.LoadBitmap(nHotImageBmpID));
		imgsHot.Add(bmpHot, clrMask);

		m_wndToolBar.Create(m_hWnd, rcDefault, NULL, /*ATL_SIMPLE_WS_CHILD | WS_VISIBLE | WS_CLIPCHILDREN | WS_CLIPSIBLINGS | 
			CCS_NOMOVEY | CCS_NODIVIDER | CCS_NORESIZE | CCS_NOPARENTALIGN |
			TBSTYLE_FLAT | */ ATL_SIMPLE_TOOLBAR_PANE_STYLE | TBSTYLE_LIST, 0);
		m_wndToolBar.SetExtendedStyle(TBSTYLE_EX_DRAWDDARROWS);
		ATLASSERT(m_wndToolBar.IsWindow());
		m_wndToolBar.SetButtonStructSize(sizeof(TBBUTTON));

		m_wndToolBar.SetImageList(imgs);
		m_wndToolBar.SetHotImageList(imgsHot);

		// add Add and Organize button
		TBBUTTON btnSp = { 2, nIDSpecial, TBSTATE_ENABLED, TBSTYLE_BUTTON | TBSTYLE_AUTOSIZE | TBSTYLE_DROPDOWN | BTNS_WHOLEDROPDOWN, 0, 0 };
		MTLVERIFY(m_wndToolBar.InsertButton(-1, &btnSp));
		TBBUTTON btnAdd = { 0, nIDAdd, TBSTATE_ENABLED, TBSTYLE_BUTTON | TBSTYLE_AUTOSIZE, 0, 0 };
		MTLVERIFY(m_wndToolBar.InsertButton(-1, &btnAdd));
		TBBUTTON btnOrg = { 1, nIDOrganize, TBSTATE_ENABLED, TBSTYLE_BUTTON | TBSTYLE_AUTOSIZE, 0, 0 };
		MTLVERIFY(m_wndToolBar.InsertButton(-1, &btnOrg));

		CVersional<TBBUTTONINFO> bi;
		bi.dwMask = TBIF_TEXT;
		bi.pszText = _T("Add...");
		MTLVERIFY(m_wndToolBar.SetButtonInfo(nIDAdd, &bi));
		bi.pszText = _T("Organize...");
		MTLVERIFY(m_wndToolBar.SetButtonInfo(nIDOrganize, &bi));
		bi.pszText = _T("View");
		MTLVERIFY(m_wndToolBar.SetButtonInfo(nIDSpecial, &bi));

		m_wndToolBar.AddStrings(_T("NS\0"));	// for proper item height

		_AddSimpleReBarBandCtrl(m_wndReBar, m_wndToolBar);

		CalcSize();
	}

	void UpdateLayout(int cxWidth, int cyHeight)
	{
		ATLASSERT(::IsWindow(m_hWnd));
		RECT rect;

		::SetRect(&rect, 0, 0, cxWidth, m_cxyHeader);
		if(m_wndReBar.m_hWnd != NULL)
			m_wndReBar.SetWindowPos(NULL, rect.left + s_cxyBorder, s_cxyBorder, rect.right - s_cxyBorder*2, rect.bottom, SWP_NOZORDER);

		if(m_view.m_hWnd != NULL) {
			CRect rc(rect.left, m_cxyHeader, cxWidth, cyHeight);
			rc.top += 1;
			rc.left += 1;
			rc.right -= 2;
			rc.bottom -= 2;
			m_view.SetWindowPos(NULL, rc, SWP_NOZORDER);
		}
		else
			rect.bottom = cyHeight;

		// I can't get the reason why I have to update now without InvalidateRect.
//		InvalidateRect(&rect); can't update a rect, correctly.
		CClientDC dc(m_hWnd);
		T* pT = static_cast<T*>(this);
		pT->DrawPaneTitle(dc.m_hDC);
	}

	void CalcSize()
	{
		CRect rcBtn;
		m_wndToolBar.GetItemRect(0, &rcBtn);
		m_cxyHeader = rcBtn.Height() + s_cxyBorder;
	}

	void DrawPaneTitle(CDCHandle dc)
	{
		CRect rect;
		GetClientRect(&rect);

//		CRect rc; m_view.GetWindowRect(&rc);
//		ScreenToClient(&rc);
		CPen pen; pen.CreatePen(PS_SOLID, 1, ::GetSysColor(COLOR_3DSHADOW));
		POINT pts[] = { { rect.right - 3, rect.top + m_cxyHeader }, { rect.left, rect.top + m_cxyHeader },
		{ rect.left, rect.bottom - 2 } };//, { rect.right - 3, rect.bottom - 1 } };

//		CRect rect_(rect);
//		rect_.top += m_cxyHeader;
//		dc.DrawEdge(&rect_, BDR_RAISEDINNER, BF_RECT | BF_FLAT);
		
//		POINT pts[] = { { rc.right - 1, rc.top - 1}, { rc.left, rc.top - 1},
//			{ rc.left, rc.bottom }, { rc.right - 1, rc.bottom } };
		HPEN hOldPen = dc.SelectPen(pen);
		dc.Polyline(pts, _countof(pts));
		dc.SelectPen(hOldPen);

		dc.DrawEdge(CRect(rect.left, rect.top + m_cxyHeader, rect.right, rect.bottom),
			EDGE_ETCHED, BF_RIGHT | BF_BOTTOM);

//		dc.DrawEdge(CRect(rect.left, rect.bottom - 2, rect.right - 2, rect.bottom + 10), EDGE_ETCHED, BF_TOP);

		rect.bottom = rect.top + m_cxyHeader;
		dc.DrawEdge(&rect, EDGE_ETCHED, BF_LEFT | BF_TOP | BF_RIGHT | BF_ADJUST);
		dc.FillRect(&rect, (HBRUSH)LongToPtr(COLOR_3DFACE + 1));
	}


	static HWND _CreateSimpleReBarCtrl(HWND hWndParent, DWORD dwStyle = ATL_SIMPLE_REBAR_STYLE, UINT nID = ATL_IDW_TOOLBAR)
	{
		// Ensure style combinations for proper rebar painting
		if(dwStyle & CCS_NODIVIDER && dwStyle & WS_BORDER)
			dwStyle &= ~WS_BORDER;
		else if(!(dwStyle & WS_BORDER) && !(dwStyle & CCS_NODIVIDER))
			dwStyle |= CCS_NODIVIDER;

		// Create rebar window
		HWND hWndReBar = ::CreateWindowEx(0, REBARCLASSNAME, NULL, dwStyle, 0, 0, 100, 100, hWndParent, (HMENU)LongToHandle(nID), _Module.GetModuleInstance(), NULL);
		if(hWndReBar == NULL)
		{
			ATLTRACE2(atlTraceUI, 0, _T("Failed to create rebar.\n"));
			return NULL;
		}

		// Initialize and send the REBARINFO structure
		REBARINFO rbi;
		rbi.cbSize = sizeof(REBARINFO);
		rbi.fMask  = 0;
		if(!::SendMessage(hWndReBar, RB_SETBARINFO, 0, (LPARAM)&rbi))
		{
			ATLTRACE2(atlTraceUI, 0, _T("Failed to initialize rebar.\n"));
			::DestroyWindow(hWndReBar);
			return NULL;
		}

		return hWndReBar;
	}

	static BOOL _AddSimpleReBarBandCtrl(HWND hWndReBar, HWND hWndBand, int nID = 0, LPTSTR lpstrTitle = NULL, BOOL bNewRow = FALSE, int cxWidth = 0, BOOL bFullWidthAlways = FALSE)
	{
		ATLASSERT(::IsWindow(hWndReBar));	// must be already created
#ifdef _DEBUG
		// block - check if this is really a rebar
		{
			TCHAR lpszClassName[sizeof(REBARCLASSNAME)];
			::GetClassName(hWndReBar, lpszClassName, sizeof(REBARCLASSNAME));
			ATLASSERT(lstrcmp(lpszClassName, REBARCLASSNAME) == 0);
		}
#endif //_DEBUG
		ATLASSERT(::IsWindow(hWndBand));	// must be already created

		// Get number of buttons on the toolbar
		int nBtnCount = (int)::SendMessage(hWndBand, TB_BUTTONCOUNT, 0, 0L);

		// Set band info structure
		REBARBANDINFO rbBand;
		rbBand.cbSize = sizeof(REBARBANDINFO);
#if (_WIN32_IE >= 0x0400)
		rbBand.fMask = RBBIM_CHILD | RBBIM_CHILDSIZE | RBBIM_STYLE | RBBIM_ID | RBBIM_SIZE | RBBIM_IDEALSIZE;
#else
		rbBand.fMask = RBBIM_CHILD | RBBIM_CHILDSIZE | RBBIM_STYLE | RBBIM_ID | RBBIM_SIZE;
#endif //!(_WIN32_IE >= 0x0400)
		if(lpstrTitle != NULL)
			rbBand.fMask |= RBBIM_TEXT;
		rbBand.fStyle = 0;
#if (_WIN32_IE >= 0x0500)
		if(nBtnCount > 0)	// add chevron style for toolbar with buttons
			rbBand.fStyle |= RBBS_USECHEVRON;
#endif //(_WIN32_IE >= 0x0500)
		if(bNewRow)
			rbBand.fStyle |= RBBS_BREAK;

		rbBand.lpText = lpstrTitle;
		rbBand.hwndChild = hWndBand;
		if(nID == 0)	// calc band ID
			nID = ATL_IDW_BAND_FIRST + (int)::SendMessage(hWndReBar, RB_GETBANDCOUNT, 0, 0L);
		rbBand.wID = nID;

		// Calculate the size of the band
		BOOL bRet;
		RECT rcTmp;
		if(nBtnCount > 0)
		{
			bRet = (BOOL)::SendMessage(hWndBand, TB_GETITEMRECT, nBtnCount - 1, (LPARAM)&rcTmp);
			ATLASSERT(bRet);
			rbBand.cx = (cxWidth != 0) ? cxWidth : rcTmp.right;
			rbBand.cyMinChild = rcTmp.bottom - rcTmp.top;
			rbBand.cxMinChild = 0;
/*			if(bFullWidthAlways)
			{
				rbBand.cxMinChild = rbBand.cx;
			}
			else if(lpstrTitle == 0)
			{
				bRet = (BOOL)::SendMessage(hWndBand, TB_GETITEMRECT, 0, (LPARAM)&rcTmp);
				ATLASSERT(bRet);
				rbBand.cxMinChild = rcTmp.right;
			}
			else
			{
				rbBand.cxMinChild = 0;
			}
*/
		}
		else	// no buttons, either not a toolbar or really has no buttons
		{
			bRet = ::GetWindowRect(hWndBand, &rcTmp);
			ATLASSERT(bRet);
			rbBand.cx = (cxWidth != 0) ? cxWidth : (rcTmp.right - rcTmp.left);
			rbBand.cxMinChild = (bFullWidthAlways) ? rbBand.cx : 0;
			rbBand.cyMinChild = rcTmp.bottom - rcTmp.top;
		}

#if (_WIN32_IE >= 0x0400)
		rbBand.cxIdeal = rbBand.cx;
#endif //(_WIN32_IE >= 0x0400)

		// Add the band
		LRESULT lRes = ::SendMessage(hWndReBar, RB_INSERTBAND, (WPARAM)-1, (LPARAM)&rbBand);
		if(lRes == 0)
		{
			ATLTRACE2(atlTraceUI, 0, _T("Failed to add a band to the rebar.\n"));
			return FALSE;
		}

		return TRUE;
	}

	BEGIN_UPDATE_COMMAND_UI_MAP(CDonutFavoritesBarImpl)
		UPDATE_COMMAND_UI_SETCHECK_FLAG(ID_FAVTREE_BAR_MYCOMPUTER, ETV_EX_MYCOMPUTER, m_view.GetExplorerTreeViewExtendedStyle())
		UPDATE_COMMAND_UI_SETCHECK_FLAG(ID_FAVTREE_BAR_STANDARD, ETV_EX_FAVORITES, m_view.GetExplorerTreeViewExtendedStyle())
		UPDATE_COMMAND_UI_SETCHECK_FLAG(ID_FAVTREE_BAR_GROUP, ETV_EX_FAVORITEGROUP, m_view.GetExplorerTreeViewExtendedStyle())
		UPDATE_COMMAND_UI_SETCHECK_FLAG(ID_FAVTREE_BAR_USER, ETV_EX_USERDEFINED, m_view.GetExplorerTreeViewExtendedStyle())
		UPDATE_COMMAND_UI_SETCHECK_FLAG(ID_FAVTREE_BAR_SHELLEXECUTE, ETV_EX_SHELLEXECUTE, m_view.GetExplorerTreeViewExtendedStyle())
		UPDATE_COMMAND_UI_SETCHECK_FLAG(ID_FAVTREE_BAR_LOADREMOTEICON, ETV_EX_LOADREMOTEICON, m_view.GetExplorerTreeViewExtendedStyle())
		UPDATE_COMMAND_UI_SETCHECK_FLAG(ID_FAVTREE_BAR_SINGLEEXPAND, ETV_EX_SINGLEEXPAND, m_view.GetExplorerTreeViewExtendedStyle())
	END_UPDATE_COMMAND_UI_MAP()
};

class CDonutFavoritesBar : public CDonutFavoritesBarImpl<CDonutFavoritesBar>
{
public:
	DECLARE_WND_CLASS_EX(_T("Donut_FavoritesBar"), 0, -1)
};

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -