スポンサーリンク

Win32apiでEDITのサイズを変えたときにそれなりのフォントサイズにする

EDITコントロールのサイズを変えるのはたやすいが、フォントサイズの指定はCreateFontでフォントを作成し、WM_SETFONTをSendMessageしなければならない。

下のプログラムは、CreateWindowで指定するときのコントロールの高さに応じて、相応のフォントサイズを計算している。

実際にこの方法を使うと、高さ50ピクセルくらいの時はいいが、100ピクセルなど巨大なテキストボックスのサイズに対してやや小さい文字となる。

そのため結果をさらに1.1~1.3倍程度するとよりちょうどよくなる(経験則)

 

///////////////////////////////////////////////////////////////////////////
// ウィンドウプロシージャ。今回はいじらない
LRESULT CALLBACK WndProc(HWND hwnd, UINT msg, WPARAM wp, LPARAM lp) {
  switch (msg) {
  case WM_DESTROY:
    DestroyWindow(hwnd);
    PostQuitMessage(0);
    return 0;
  }
  return DefWindowProc(hwnd, msg, wp, lp);
}

int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,
  PSTR lpCmdLine, int nCmdShow) {
  HWND hwnd_parent;
  MSG msg;
  WNDCLASS winc;
  ///////////////////////////////////////////////////////////////////////////
  // ウィンドウクラスの登録。特別なことはしない
  winc.style = CS_HREDRAW | CS_VREDRAW;
  winc.lpfnWndProc = WndProc;
  winc.cbClsExtra = winc.cbWndExtra = 0;
  winc.hInstance = hInstance;
  winc.hIcon = LoadIcon(NULL, IDI_APPLICATION);
  winc.hCursor = LoadCursor(NULL, IDC_ARROW);
  winc.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH);
  winc.lpszMenuName = NULL;
  winc.lpszClassName = TEXT("MYWINDOW");

  if (!RegisterClass(&winc)) return 0;

 ///////////////////////////////////////////////////////////////////////////
 // メインウィンドウの作成。特別なことはしない
  hwnd_parent = CreateWindow(
    TEXT("MYWINDOW"), TEXT("my window"),
    WS_OVERLAPPEDWINDOW | WS_VISIBLE,
    100, 100, 200, 200, NULL, NULL,
    hInstance, NULL
  );
 if (hwnd_parent == NULL) return 0; 
 ///////////////////////////////////////////////////////////////////////////
 // エディットボックスの作成。内容的に普通。
  int edit_height = 300;//高さを変数指定する。この高さを基準にフォントサイズを決定するため。
  HWND hedit = CreateWindow(
    TEXT("EDIT"), TEXT("edit box"),
    WS_CHILD | WS_VISIBLE | WS_BORDER | ES_LEFT,
    0, 0, 500, edit_height, hwnd_parent, (HMENU)1,
    hInstance,
    NULL
  );

  //http://d.hatena.ne.jp/It_lives_vainly/20100331/1270002338
  //${フォントのポイント数} × ${利用ディスプレイのDPI} ÷ 72 = ${フォント表示のドット数(高さ)}
  // → ${フォントのポイント数}  = ${フォント表示のドット数(高さ)} * 72 ÷ ${利用ディスプレイのDPI}
  double wdpi, hdpi,sdpi;
  GetDPI(hedit, &wdpi, &hdpi,&sdpi); //DPIを求める関数(自作)を呼び出し
  int pt = edit_height * 72 / hdpi;  // フォントサイズをポイントで求める
                                     // DPIを計算すると大体1.33になるので、 pt = edit_height / 1.33;でもいい
  ////////////////////////////////////////////
  //フォント作成 /////////////////////////////
  ///////////////////////////////////////////
  HDC editdc = GetDC(hedit);
  int lfHeight = pt;
  HFONT hEditFont = CreateFont(lfHeight, 0, 0, 0,
    FW_NORMAL, FALSE, FALSE, 0,
    SHIFTJIS_CHARSET,
    OUT_DEFAULT_PRECIS,
    CLIP_DEFAULT_PRECIS,
    DEFAULT_QUALITY, DEFAULT_PITCH, "MS Pゴシック" );
  ReleaseDC(hedit,editdc);
  //////////////////////////////////////////
  //フォント変更のメッセージを送信 //////////
  //////////////////////////////////////////
  SendMessage(hedit, WM_SETFONT, (WPARAM)hEditFont, MAKELPARAM(TRUE, 0));


  while (GetMessage(&msg, NULL, 0, 0)) {
    TranslateMessage(&msg);
    DispatchMessage(&msg);
  }

  DeleteObject(hEditFont);


  return msg.wParam;
}

 

 

 

GetDPIの中身はこのようになる。

//参考↓
//https://gist.github.com/skitaoka/842b8d6cbb00bb54d9ef430dd082e822
void GetDPI(HWND hwnd,double *width_DPI,double* height_DPI,double* size_DPI) {
  HDC hdc = GetDC(hwnd);

  // 画面解像度を取得
  const int width_pix = GetDeviceCaps(hdc, HORZRES);
  const int height_pix = GetDeviceCaps(hdc, VERTRES);
  const double size_pix = std::sqrt(width_pix * width_pix + height_pix * height_pix);

  // 物理サイズを取得 (単位は mm)
  const int width_mm = GetDeviceCaps(hdc, HORZSIZE);
  const int height_mm = GetDeviceCaps(hdc, VERTSIZE);

  // インチサイズに換算
  const double width_inch = width_mm / 25.4;
  const double height_inch = height_mm / 25.4;
  const double size_inch = std::sqrt(width_inch * width_inch + height_inch * height_inch);

  // DPI を算出
  const double width_dpi = width_pix / width_inch;
  const double height_dpi = height_pix / height_inch;
  const double size_dpi = size_pix / size_inch;

  *width_DPI = width_dpi;
  *height_DPI = height_dpi;
  *size_DPI = size_dpi;

  ReleaseDC(hwnd, hdc);
}

 

 

EditBox高さ30 px

edit_font_height_30

 

EditBox高さ60 px

edit_font_height_60

EditBox高さ100 px

edit_font_height_100

 

コメントを残す

メールアドレスが公開されることはありません。

日本語が含まれない投稿は無視されますのでご注意ください。(スパム対策)


この記事のトラックバックURL: