Исчерпывающее руководство по написанию всплывающих подсказок | страница 19



>  CString strItem;

>  GetText(nIndex, strItem);

>  if (!strItem.IsEmpty()) {

>   // Вычислить длину идеального текста.

>   CClientDC DC(this);

>   CFont* pOldFont = DC.SelectObject(GetFont());

>   CSize ItemSize = DC.GetTextExtent(strItem);

>   DC.SelectObject(pOldFont);

>   // Взять максимум от обычной ширины и идеальной ширины.

>   const int cxEdgeSpace = 2;

>   lpRect->right = max(lpRect->right, lpRect->left + ItemSize.cx + (cxEdgeSpace * 2));

>  }

> } else {

>  TRACE("Owner-draw listbox detected – override CTitleTipListBox::GetIdeaItemRect()\n");

> }

> return nStatus;

>}


>void CTitleTipListBox::AdjustTitleTip(int nNewIndex) {

> if (!::IsWindow(m_TitleTip.m_hWnd)) {

>  VERIFY(m_TitleTip.Create(this));

> }

> if (nNewIndex == m_nNoIndex) {

>  m_TitleTip.Hide();

> } else {

>  CRect IdealItemRect;

>  GetIdealItemRect(nNewIndex, IdealItemRect);

>  CRect ItemRect;

>  GetItemRect(nNewIndex, ItemRect);

>  if (ItemRect == IdealItemRect) {

>   m_TitleTip.Hide();

>  } else {

>   // Поправить координаты рядом с краем экрана.

>   ClientToScreen(IdealItemRect);

>   int nScreenWidth = ::GetSystemMetrics(SM_CXFULLSCREEN);

>   if (IdealItemRect.right > nScreenWidth) {

>    IdealItemRect.OffsetRect(nScreenWidth – IdealItemRect.right, 0);

>   }

>   if (IdealItemRect.left < 0) {

>    IdealItemRect.OffsetRect(-IdealItemRect.left, 0);

>   }

>   m_TitleTip.Show(IdealItemRect, nNewIndex);

>  }

> }

> if (m_TitleTip.IsWindowVisible()) {

>  // Удостовериться, что мышь захвачена, чтобы отследить

>  // момент отключения подсказки.

>  if (!m_bMouseCaptured && GetCapture() != this) {

>   CaptureMouse();

>  }

> } else {

>  // Подсказка невидима, поэтому освободить мышь.

>  if (m_bMouseCaptured) {

>   VERIFY(ReleaseCapture());

>   m_bMouseCaptured = FALSE;

>  }

> }

>}


>void CTitleTipListBox::CaptureMouse() {

> ASSERT(!m_bMouseCaptured);

> CPoint Point;

> VERIFY(GetCursorPos(&Point));

> ScreenToClient(&Point);

> m_LastMouseMovePoint = Point;

> SetCapture();

> m_bMouseCaptured = TRUE;

>}


>/////////////////////////////////////////////////////////////////////////////

>// CTitleTipListBox message handlers

>LONG CTitleTipListBox::OnContentChanged(UINT, LONG) {

> // Turn off title tip.

> AdjustTitleTip(m_nNoIndex);

> return Default();

>}


>void CTitleTipListBox::OnMouseMove(UINT nFlags, CPoint point) {

> if (point != m_LastMouseMovePoint && IsAppActive()) {

>  m_LastMouseMovePoint = point;

>  int nIndexHit = m_nNoIndex;

>  CRect ClientRect;

>  GetClientRect(ClientRect);

>  if (ClientRect.PtInRect(point)) {

>   // Hit test.

>   for (int n = 0; nIndexHit == m_nNoIndex && n < GetCount(); n++) {