web-dev-qa-db-ja.com

Win32のウィンドウ境界の幅と高さ-どうすれば取得できますか?

 :: GetSystemMetrics(SM_CYBORDER)

... 1で戻り、タイトルバーが1ピクセルよりも高いことを知っています:/

私も試しました:

 RECT r; 
 r.left = r.top = 0; r.right = r.bottom = 400; 
 :: AdjustWindowRect(&r、WS_OVERLAPPED、FALSE); 
 _bdW =(uword)(r.right-r.left-400); 
 _bdH =(uword)(r.bottom-r.top-400); 

しかし、境界w、hは0として戻ってきました。

私のWM_SIZEハンドラーでは、ウィンドウの高さが「ステップ」で変化することを確認する必要があります。たとえば、テキストの新しい行全体がウィンドウに収まり、下部に「ジャンクな部分的な行スペース」がないようにする必要があります。

ただし、:: MoveWindowには、境界線スペースを追加した寸法が必要です。

誰かが前にこれをやったはずです...助けてくれてありがとう:)

27
Stephen Hazel

GetWindowRect および GetClientRect 関数を使用して、すべてのウィンドウ境界のサイズを計算できます。

Suite101には ウィンドウのサイズを変更し、クライアント領域を既知のサイズに保つ に関する記事があります。

これがサンプルコードです。

void ClientResize(HWND hWnd, int nWidth, int nHeight)
{
  RECT rcClient, rcWind;
  POINT ptDiff;
  GetClientRect(hWnd, &rcClient);
  GetWindowRect(hWnd, &rcWind);
  ptDiff.x = (rcWind.right - rcWind.left) - rcClient.right;
  ptDiff.y = (rcWind.bottom - rcWind.top) - rcClient.bottom;
  MoveWindow(hWnd,rcWind.left, rcWind.top, nWidth + ptDiff.x, nHeight + ptDiff.y, TRUE);
}
39
stukelly
_int border_thickness = GetSystemMetrics(SM_CXSIZEFRAME);
_

実際、上記の結果は次のようになります。

_GetClientRect(hWnd, &rcClient); 
GetWindowRect(hWnd, &rcWind); 
int border_thickness = ((rcWind.right - rcWind.left) - rcClient.right) / 2; 
_

しかしGetSystemMetrics(SM_CXSIZEFRAME)の方が使いやすいです。

12
Tody.Lu

あなたが探しているのはSM_CYCAPTION-タイトルバーの高さです。 SM_CYBORDERは、ウィンドウの水平エッジの高さです。

11
Head Geek

Stukellyによって提案された方法は、ウィンドウが最小化されていないか、完全に初期化されていない限り機能します。これらの条件で境界線サイズを提供する別の方法は、AdjustWindowRectEx関数を使用することです。次に例を示します。

CSize GetBorderSize(const CWnd& window)
{
   // Determine the border size by asking windows to calculate the window rect
   // required for a client rect with a width and height of 0
   CRect rect;
   AdjustWindowRectEx(&rect, window.GetStyle(), FALSE, window.GetExStyle());
   return rect.Size();
}

アプリケーションによっては、現在表示されている境界線のサイズが必要な場合、このアプローチとstukellyのアプローチを組み合わせる必要がある場合があります。

CSize GetBorderSize(const CWnd& window)
{
   if (window.IsZoomed())
   {
      // The total border size is found by subtracting the size of the client rect
      // from the size of the window rect. Note that when the window is zoomed, the
      // borders are hidden, but the title bar is not.
      CRect wndRect, clientRect;
      window.GetWindowRect(&wndRect);
      window.GetClientRect(&clientRect);
      return wndRect.Size() - clientRect.Size();
   }
   else
   {
      // Determine the border size by asking windows to calculate the window rect
      // required for a client rect with a width and height of 0. This method will
      // work before the window is fully initialized and when the window is minimized.
      CRect rect;
      AdjustWindowRectEx(&rect, window.GetStyle(), FALSE, window.GetExStyle());
      return rect.Size();
   }
}
3
Thomas M

Head Geekが詳細な答えを提供します。GetSystemMetricsを使用して、キャプションとボーダービットを加算します。 GetWindowRectとGetClientRectの間で幅/高さを変更することもできます。これにより、すべてのキャプション/境界線などの合計が得られます。

2
CodeGuy

別の解決策があります... WM_CREATEおよびWM_INITDIALOGメッセージで専用関数を呼び出すことにより、境界を事前に計算できます。また、ウィンドウスタイルを変更したり、メニューを2行に分割したりする場合は、値を更新します。

RECT cRect, wRect, oRect;
GetWindowRect(hWnd, &wRect);
GetClientRect(hWnd, &cRect);
MapWindowPoints(hWnd, NULL, (LPPOINT)&cRect, 2);

oRect.left = cRect.left - wRect.left;
oRect.top = cRect.top - wRect.top;
oRect.right = wRect.right - cRect.right;
oRect.bottom = wRect.bottom - cRect.bottom;
0
user11109368