4 WIN32_OP( Create(p_parent) != NULL );
7 if (m_hWnd != NULL) DestroyWindow();
16 virtual
bool QueryHint(
unsigned p_id,
pfc::string_base & p_out) {
22 if (HIWORD(p_wp) & MF_POPUP) {
26 if (!QueryHint(LOWORD(p_wp),msg)) {
51 void Set(
unsigned p_id,
const char * p_description) {m_content.set(p_id,p_description);}
54 return m_content.query(p_id,p_out);
63 void Set(
unsigned id,
const char * desc) {m_content.set(
id, desc);}
65 void SetCM(contextmenu_manager::ptr mgr,
unsigned base,
unsigned max) {
66 m_cmMgr = mgr; m_cmMgr_base = base; m_cmMgr_max = max;
70 if (m_cmMgr.is_valid() && p_id >= m_cmMgr_base && p_id < m_cmMgr_max) {
71 return m_cmMgr->get_description_by_id(p_id - m_cmMgr_base,p_out);
73 return m_content.query(p_id,p_out);
77 contextmenu_manager::ptr m_cmMgr;
unsigned m_cmMgr_base,
m_cmMgr_max;
81 return p_fmt <<
"(" << p_point.x <<
"," << p_point.y <<
")";
85 return p_fmt <<
"(" << p_rect.left <<
"," << p_rect.top <<
"," << p_rect.right <<
"," << p_rect.bottom <<
")";
88 template<
typename TClass>
98 return _parentClass::ProcessWindowMessage(hWnd, uMsg, wParam, lParam, lResult, dwMsgMapID);
104 template<
typename TClass>
109 template<
typename TParam1>
CWindowAutoLifetime(HWND parent,
const TParam1 & p1) : TBase(p1) {Init(parent);}
110 template<
typename TParam1,
typename TParam2>
CWindowAutoLifetime(HWND parent,
const TParam1 & p1,
const TParam2 & p2) : TBase(p1,p2) {Init(parent);}
111 template<
typename TParam1,
typename TParam2,
typename TParam3>
CWindowAutoLifetime(HWND parent,
const TParam1 & p1,
const TParam2 & p2,
const TParam3 & p3) : TBase(p1,p2,p3) {Init(parent);}
112 template<
typename TParam1,
typename TParam2,
typename TParam3,
typename TParam4>
CWindowAutoLifetime(HWND parent,
const TParam1 & p1,
const TParam2 & p2,
const TParam3 & p3,
const TParam4 & p4) : TBase(p1,p2,p3,p4) {Init(parent);}
113 template<
typename TParam1,
typename TParam2,
typename TParam3,
typename TParam4,
typename TParam5>
CWindowAutoLifetime(HWND parent,
const TParam1 & p1,
const TParam2 & p2,
const TParam3 & p3,
const TParam4 & p4,
const TParam5 & p5) : TBase(p1,p2,p3,p4,p5) {Init(parent);}
114 template<
typename TParam1,
typename TParam2,
typename TParam3,
typename TParam4,
typename TParam5,
typename TParam6>
CWindowAutoLifetime(HWND parent,
const TParam1 & p1,
const TParam2 & p2,
const TParam3 & p3,
const TParam4 & p4,
const TParam5 & p5,
const TParam6 & p6) : TBase(p1,p2,p3,p4,p5,p6) {Init(parent);}
116 void Init(HWND parent) {WIN32_OP(this->Create(parent) != NULL);}
117 void OnFinalMessage(HWND wnd) {PFC_ASSERT_NO_EXCEPTION( TBase::OnFinalMessage(wnd) ); PFC_ASSERT_NO_EXCEPTION(
delete this);}
120 template<
typename TClass>
126 MSG_WM_INITDIALOG(OnInitDialog)
127 MSG_WM_DESTROY(OnDestroy)
128 CHAIN_MSG_MAP(TClass)
131 BOOL OnInitDialog(CWindow, LPARAM) {m_modeless.Set( m_hWnd ); SetMsgHandled(FALSE);
return FALSE; }
132 void OnDestroy() {m_modeless.Set(NULL); SetMsgHandled(FALSE); }
141 return m_owner->edit_mode_context_menu_get_description(p_id,m_id_base,p_out);
153 if (!p_elem->edit_mode_context_menu_get_focus_point(pt)) {
155 WIN32_OP_D( GetWindowRect(p_elem->get_wnd(), rc) );
156 pt = rc.CenterPoint();
159 fromKeyboard =
false;
162 if (p_elem->edit_mode_context_menu_test(pt,fromKeyboard)) {
163 const unsigned idBase = 1;
165 WIN32_OP( menu.CreatePopupMenu() );
166 p_elem->edit_mode_context_menu_build(pt,fromKeyboard,menu,idBase);
171 cmd = menu.TrackPopupMenu(TPM_RIGHTBUTTON|TPM_NONOTIFY|TPM_RETURNCMD,pt.x,pt.y,receiver);
173 if (cmd > 0) p_elem->edit_mode_context_menu_command(pt,fromKeyboard,cmd,idBase);
185 #if _WIN32_WINNT >= 0x501 187 const int total = header.GetItemCount();
188 for(
int walk = 0; walk < total; ++walk) {
189 HDITEM item = {}; item.mask = HDI_FORMAT;
190 if (header.GetItem(walk,&item)) {
191 DWORD newFormat = item.fmt;
192 newFormat &= ~( HDF_SORTUP | HDF_SORTDOWN );
193 if (walk == column) {
194 newFormat |= isUp ? HDF_SORTUP : HDF_SORTDOWN;
196 if (newFormat != item.fmt) {
197 item.fmt = newFormat;
198 header.SetItem(walk,&item);
205 typedef CWinTraits<WS_POPUP,WS_EX_TRANSPARENT|WS_EX_LAYERED|WS_EX_TOPMOST|WS_EX_TOOLWINDOW>
CFlashWindowTraits;
212 SetTimer(KTimerID, 500);
215 ShowWindow(SW_HIDE); KillTimer(KTimerID);
219 if (m_hWnd == NULL) {
220 WIN32_OP( Create(NULL) != NULL );
223 WIN32_OP_D( parent.GetWindowRect(rect) );
224 WIN32_OP_D( SetWindowPos(NULL,rect,SWP_NOZORDER | SWP_NOACTIVATE | SWP_SHOWWINDOW) );
229 if (m_hWnd != NULL) DestroyWindow();
233 MSG_WM_CREATE(OnCreate)
234 MSG_WM_TIMER(OnTimer)
235 MSG_WM_DESTROY(OnDestroy)
240 void OnDestroy() throw() { 244 KTimerID = 0x47f42dd0 246 void OnTimer(WPARAM id) { 247 if (id == KTimerID) { 248 switch(++m_tickCount) { 262 LRESULT OnCreate(LPCREATESTRUCT) throw() { 263 SetLayeredWindowAttributes(*this,0,128,LWA_ALPHA); 267 t_uint32 m_tickCount; 270 class CTypableWindowScope { 272 CTypableWindowScope() : m_wnd() {} 273 ~CTypableWindowScope() {Set(NULL);} 277 static_api_ptr_t<ui_element_typable_window_manager>()->remove(m_wnd); 281 static_api_ptr_t<ui_element_typable_window_manager>()->add(m_wnd); 283 } catch(exception_service_not_found) { 290 PFC_CLASS_NOT_COPYABLE_EX(CTypableWindowScope); 294 template<typename TBase> class CContainedWindowSimpleT : public CContainedWindowT<TBase>, public CMessageMap { 296 CContainedWindowSimpleT() : CContainedWindowT<TBase>(this) {} 297 BEGIN_MSG_MAP(CContainedWindowSimpleT) 302 static bool window_service_trait_defer_destruction(const service_base *) {return true;} 306 template<typename _t_base> 307 class window_service_impl_t : public CWindowFixSEH<_t_base> { 309 typedef window_service_impl_t<_t_base> t_self; 310 typedef CWindowFixSEH<_t_base> t_base; 312 BEGIN_MSG_MAP_EX(window_service_impl_t) 313 MSG_WM_DESTROY(OnDestroyPassThru) 314 CHAIN_MSG_MAP(__super) 317 int FB2KAPI service_release() throw() { 318 int ret = --m_counter; 320 if (window_service_trait_defer_destruction(this) && !InterlockedExchange(&m_delayedDestroyInProgress,1)) { 321 PFC_ASSERT_NO_EXCEPTION( service_impl_helper::release_object_delayed(this); ); 322 } else if (m_hWnd != NULL) { 323 if (!m_destroyWindowInProgress) { // don't double-destroy in weird scenarios 324 PFC_ASSERT_NO_EXCEPTION( ::DestroyWindow(m_hWnd) ); 327 PFC_ASSERT_NO_EXCEPTION( delete this ); 332 int FB2KAPI service_add_ref() throw() {return ++m_counter;} 334 TEMPLATE_CONSTRUCTOR_FORWARD_FLOOD_WITH_INITIALIZER(window_service_impl_t,t_base,{m_destroyWindowInProgress = false; m_delayedDestroyInProgress = 0; }) 336 void OnDestroyPassThru() { 337 SetMsgHandled(FALSE); m_destroyWindowInProgress = true; 339 void OnFinalMessage(HWND p_wnd) { 340 t_base::OnFinalMessage(p_wnd); 341 service_ptr_t<service_base> bump(this); 343 volatile bool m_destroyWindowInProgress; 344 volatile LONG m_delayedDestroyInProgress; 345 pfc::refcounter m_counter; 349 static void AppendMenuPopup(HMENU menu, UINT flags, CMenu & popup, const TCHAR * label) { 350 PFC_ASSERT( flags & MF_POPUP ); 351 WIN32_OP( CMenuHandle(menu).AppendMenu(flags, popup, label) ); 355 class CMessageMapDummy : public CMessageMap { 357 BOOL ProcessWindowMessage(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, 358 LRESULT& lResult, DWORD dwMsgMapID) {return FALSE;} 361 class CPopupTooltipMessage { 363 CPopupTooltipMessage(DWORD style = TTS_BALLOON | TTS_NOPREFIX) : m_style(style | WS_POPUP), m_toolinfo(), m_shutDown() {} 364 void ShowFocus(const TCHAR * message, CWindow wndParent) { 365 Show(message, wndParent); wndParent.SetFocus(); 367 void Show(const TCHAR * message, CWindow wndParent) { 368 if (m_shutDown || (message == NULL && m_tooltip.m_hWnd == NULL)) return; 372 if (message != NULL) { 374 WIN32_OP_D( wndParent.GetWindowRect(rect) ); 375 ShowInternal(message, wndParent, rect); 378 void ShowEx(const TCHAR * message, CWindow wndParent, CRect rect) { 379 if (m_shutDown) return; 382 ShowInternal(message, wndParent, rect); 385 if (m_tooltip.m_hWnd != NULL && m_tooltip.GetToolCount() > 0) { 386 m_tooltip.TrackActivate(&m_toolinfo,FALSE); 387 m_tooltip.DelTool(&m_toolinfo); 392 if (m_tooltip.m_hWnd != NULL) { 393 m_tooltip.DestroyWindow(); 397 m_shutDown = true; CleanUp(); 400 void ShowInternal(const TCHAR * message, CWindow wndParent, CRect rect) { 401 PFC_ASSERT( !m_shutDown ); 402 PFC_ASSERT( message != NULL ); 403 PFC_ASSERT( wndParent != NULL ); 404 m_toolinfo.cbSize = sizeof(m_toolinfo); 405 m_toolinfo.uFlags = TTF_TRACK|TTF_IDISHWND|TTF_ABSOLUTE|TTF_TRANSPARENT|TTF_CENTERTIP; 406 m_toolinfo.hwnd = wndParent; 408 m_toolinfo.lpszText = const_cast<TCHAR*>(message); 409 m_toolinfo.hinst = NULL; //core_api::get_my_instance(); 410 if (m_tooltip.AddTool(&m_toolinfo)) { 411 m_tooltip.TrackPosition(rect.CenterPoint().x,rect.bottom); 412 m_tooltip.TrackActivate(&m_toolinfo,TRUE); 416 if (m_tooltip.m_hWnd == NULL) { 417 WIN32_OP( m_tooltip.Create( NULL , NULL, NULL, m_style) ); 420 CContainedWindowSimpleT<CToolTipCtrl> m_tooltip; 427 template<typename T> class CDialogWithTooltip : public CDialogImpl<T> { 429 BEGIN_MSG_MAP(CDialogWithTooltip) 430 MSG_WM_DESTROY(OnDestroy) 433 void ShowTip(UINT id, const TCHAR * label) { 434 m_tip.Show(label, GetDlgItem(id)); 436 void ShowTip(HWND child, const TCHAR * label) { 437 m_tip.Show(label, child); 440 void ShowTipF(UINT id, const TCHAR * label) { 441 m_tip.ShowFocus(label, GetDlgItem(id)); 443 void ShowTipF(HWND child, const TCHAR * label) { 444 m_tip.ShowFocus(label, child); 446 void HideTip() {m_tip.Hide();} 448 void OnDestroy() {m_tip.ShutDown(); SetMsgHandled(FALSE); } 449 CPopupTooltipMessage m_tip; 459 static void ListView_FixContextMenuPoint(CListViewCtrl list,CPoint & coords) { 460 if (coords == CPoint(-1,-1)) { 462 CRect rcClient; WIN32_OP_D(list.GetClientRect(rcClient)); 464 selWalk = list.GetNextItem(selWalk, LVNI_SELECTED); 467 WIN32_OP_D( list.GetWindowRect(&rc) ); 468 coords = rc.CenterPoint(); 471 CRect rcItem, rcVisible; 472 WIN32_OP_D( list.GetItemRect(selWalk, &rcItem, LVIR_BOUNDS) ); 473 if (rcVisible.IntersectRect(rcItem, rcClient)) { 474 coords = rcVisible.CenterPoint(); 475 WIN32_OP_D( list.ClientToScreen(&coords) ); 483 template<typename TDialog> class preferences_page_instance_impl : public TDialog { 485 preferences_page_instance_impl(HWND parent, preferences_page_callback::ptr callback) : TDialog(callback) {WIN32_OP(this->Create(parent) != NULL);} 486 HWND get_wnd() {return this->m_hWnd;} 488 static bool window_service_trait_defer_destruction(const preferences_page_instance *) {return false;} 489 template<typename TDialog> class preferences_page_impl : public preferences_page_v3 { 491 preferences_page_instance::ptr instantiate(HWND parent, preferences_page_callback::ptr callback) { 492 return new window_service_impl_t<preferences_page_instance_impl<TDialog> >(parent, callback); 496 class CEmbeddedDialog : public CDialogImpl<CEmbeddedDialog> { 498 CEmbeddedDialog(CMessageMap * owner, DWORD msgMapID, UINT dialogID) : m_owner(*owner), IDD(dialogID), m_msgMapID(msgMapID) {} 500 BEGIN_MSG_MAP(CEmbeddedDialog) 501 CHAIN_MSG_MAP_ALT_MEMBER(m_owner, m_msgMapID) 504 const DWORD m_msgMapID; 506 CMessageMap & m_owner; 510 void PaintSeparatorControl(CWindow wnd); 512 class CStaticSeparator : public CContainedWindowT<CStatic>, private CMessageMap { 514 CStaticSeparator() : CContainedWindowT<CStatic>(this, 0) {} 515 BEGIN_MSG_MAP_EX(CSeparator) 516 MSG_WM_PAINT(OnPaint) 517 MSG_WM_SETTEXT(OnSetText) 520 int OnSetText(LPCTSTR lpstrText) { 522 SetMsgHandled(FALSE); 525 void OnPaint(CDCHandle) { 526 PaintSeparatorControl(*this); 532 template<typename TClass> 533 class CTextControl : public CWindowRegisteredT<TClass> { 535 BEGIN_MSG_MAP_EX(CTextControl) 536 MSG_WM_SETFONT(OnSetFont) 537 MSG_WM_GETFONT(OnGetFont) 538 MSG_WM_SETTEXT(OnSetText) 539 CHAIN_MSG_MAP(__super) 545 void OnSetFont(HFONT font, BOOL bRedraw) { 547 if (bRedraw) Invalidate(); 549 int OnSetText(LPCTSTR lpstrText) { 550 Invalidate();SetMsgHandled(FALSE); return 0; 555 #ifndef VSCLASS_TEXTSTYLE 557 // TEXTSTYLE class parts and states 559 #define VSCLASS_TEXTSTYLE L"TEXTSTYLE
" 561 enum TEXTSTYLEPARTS { 562 TEXT_MAININSTRUCTION = 1, 563 TEXT_INSTRUCTION = 2, 566 TEXT_SECONDARYTEXT = 5, 567 TEXT_HYPERLINKTEXT = 6, 570 TEXT_CONTROLLABEL = 9, 573 enum HYPERLINKTEXTSTATES { 574 TS_HYPERLINK_NORMAL = 1, 575 TS_HYPERLINK_HOT = 2, 576 TS_HYPERLINK_PRESSED = 3, 577 TS_HYPERLINK_DISABLED = 4, 580 enum CONTROLLABELSTATES { 581 TS_CONTROLLABEL_NORMAL = 1, 582 TS_CONTROLLABEL_DISABLED = 2, 588 class CStaticThemed : public CContainedWindowT<CStatic>, private CMessageMap { 590 CStaticThemed() : CContainedWindowT<CStatic>(this, 0), m_id(), m_fallback() {} 591 BEGIN_MSG_MAP_EX(CStaticThemed) 592 MSG_WM_PAINT(OnPaint) 593 MSG_WM_THEMECHANGED(OnThemeChanged) 594 MSG_WM_SETTEXT(OnSetText) 597 void SetThemePart(int id) {m_id = id; if (m_hWnd != NULL) Invalidate();} 599 int OnSetText(LPCTSTR lpstrText) { 601 SetMsgHandled(FALSE); 604 void OnThemeChanged() { 608 void OnPaint(CDCHandle) { 610 SetMsgHandled(FALSE); return; 612 if (m_theme == NULL) { 613 m_theme.OpenThemeData(*this, L"TextStyle
"); 614 if (m_theme == NULL) { 615 m_fallback = true; SetMsgHandled(FALSE); return; 619 TCHAR buffer[512] = {}; 620 GetWindowText(buffer, _countof(buffer)); 621 const int txLen = pfc::strlen_max_t(buffer, _countof(buffer)); 623 WIN32_OP_D( GetClientRect(contentRect) ); 624 SelectObjectScope scopeFont(dc, GetFont()); 625 dc.SetTextColor(GetSysColor(COLOR_WINDOWTEXT)); 626 dc.SetBkMode(TRANSPARENT); 629 CRect rcText(contentRect); 631 DWORD style = GetStyle(); 632 if (style & SS_LEFT) flags |= DT_LEFT; 633 else if (style & SS_RIGHT) flags |= DT_RIGHT; 634 else if (style & SS_CENTER) flags |= DT_CENTER; 635 if (style & SS_ENDELLIPSIS) flags |= DT_END_ELLIPSIS; 637 HRESULT retval = DrawThemeText(m_theme, dc, m_id, 0, buffer, txLen, flags, 0, rcText); 638 PFC_ASSERT( SUCCEEDED( retval ) ); 645 class CStaticMainInstruction : public CStaticThemed { 647 CStaticMainInstruction() { SetThemePart(TEXT_MAININSTRUCTION); } 652 class CSeparator : public CTextControl<CSeparator> { 654 BEGIN_MSG_MAP_EX(CSeparator) 655 MSG_WM_PAINT(OnPaint) 656 CHAIN_MSG_MAP(__super) 659 static const TCHAR * GetClassName() { 660 return _T("foobar2000:separator
"); 663 void OnPaint(CDCHandle dc) { 664 PaintSeparatorControl(*this);
pfc::string_base & operator<<(pfc::string_base &p_fmt, const CPoint &p_point)
BEGIN_MSG_MAP_EX(CFlashWindow) MSG_WM_CREATE(OnCreate) MSG_WM_TIMER(OnTimer) MSG_WM_DESTROY(OnDestroy) END_MSG_MAP() DECLARE_WND_CLASS_EX(TEXT("
CWindowAutoLifetime(HWND parent)
CWindowAutoLifetime(HWND parent, const TParam1 &p1, const TParam2 &p2, const TParam3 &p3, const TParam4 &p4, const TParam5 &p5)
LONG SHARED_EXPORT uExceptFilterProc(LPEXCEPTION_POINTERS param)
void ShowAbove(CWindow parent)
typedef BOOL(WINAPI *pPowerSetRequest_t)(__in HANDLE PowerRequest
BEGIN_MSG_MAP_EX(ImplementModelessTracking) MSG_WM_INITDIALOG(OnInitDialog) MSG_WM_DESTROY(OnDestroy) CHAIN_MSG_MAP(TClass) END_MSG_MAP_HOOK() private
void OnFinalMessage(HWND wnd)
static void HeaderControl_SetSortIndicator(CHeaderCtrl header, int column, bool isUp)
BOOL ProcessWindowMessage(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, LRESULT &lResult, DWORD dwMsgMapID=0)
CWinTraits< WS_POPUP, WS_EX_TRANSPARENT|WS_EX_LAYERED|WS_EX_TOPMOST|WS_EX_TOOLWINDOW > CFlashWindowTraits
void complain(const char *what, const char *msg)
CModelessDialogEntry m_modeless
CWindowAutoLifetime(HWND parent, const TParam1 &p1, const TParam2 &p2, const TParam3 &p3)
CWindowAutoLifetime(HWND parent, const TParam1 &p1)
CWindowAutoLifetime(HWND parent, const TParam1 &p1, const TParam2 &p2)
CWindowFixSEH< TClass > TBase
static void ui_element_instance_standard_context_menu_eh(service_ptr_t< ui_element_instance > p_elem, LPARAM p_pt)
static void ui_element_instance_standard_context_menu(service_ptr_t< ui_element_instance > p_elem, LPARAM p_pt)
Helper template used to easily access core services. Usage: static_api_ptr_t<myclass> api; api->doso...
CWindowAutoLifetime(HWND parent, const TParam1 &p1, const TParam2 &p2, const TParam3 &p3, const TParam4 &p4, const TParam5 &p5, const TParam6 &p6)
void Activate(CWindow parent)
CWindowAutoLifetime(HWND parent, const TParam1 &p1, const TParam2 &p2, const TParam3 &p3, const TParam4 &p4)