Dapatkan ukuran total TCheckbox, termasuk kotak dan teks, di Delphi

Jan 15 2021

Saya ingin mendapatkan ukuran total dari TCheckbox, termasuk kotak dan teks dalam Delphi. Saya memeriksa artikel di Delphi FMX TCheckbox / TRadiobutton Autosize , tetapi tampaknya TCheckbox tidak memiliki properti Canvas sehingga kodenya tidak cocok untuk itu.

Memperbarui

Izinkan saya menjelaskan alasan mengapa saya perlu mengetahuinya. Di beberapa kotak centang saya, saya perlu memasukkan spinedit terkait dengan kotak centang tersebut. Misalnya, di kotak centang "Pisahkan file jika ukurannya lebih besar dari" ### "Bytes", di mana ### adalah spin edit.

Karena kotak centang tidak mendukung ukuran otomatis, salah satu caranya adalah memperbesar kotak centang sehingga menampung semua teks. Kemudian letakkan spin edit setelah karakter terlihat terakhir.

Ini bagus untuk satu bahasa, namun, untuk mendukung multi-bahasa, beberapa bahasa akan lebih panjang dari yang lain.

Dalam kasus seperti itu, saya dapat memilih:

  1. Hitung ukuran bagian checkbxo yang terlihat.

atau

  1. Jaga beberapa spasi antara karakter terakhir yang terlihat dan pengeditan putaran.

metode 2 tidak terlalu bagus karena akan ada jarak yang sangat jauh antara kotak centang dan edit putaran untuk beberapa bahasa.

Perbarui 2

Satu masalah lagi, saya mencoba melakukan hal yang sama untuk sebuah tombol, seperti di bawah ini:

var
  bmp: TBitmap;
  size: TSize;
  width: Integer;
begin
  Checkbox1.Caption := Edit3.Text;
  Button3.Caption := Edit3.Text;

  bmp := TBitmap.Create;
  try
    bmp.SetSize(CheckBox1.Width, CheckBox1.Height);
    bmp.Canvas.Font := CheckBox1.Font;
    size := bmp.Canvas.TextExtent(CheckBox1.Caption);
    Width := bmp.Canvas.TextWidth(Checkbox1.Caption);
    CheckBox1.Width := size.cx + 20;
    button3.Width := size.cx;
    SpinEdit1.Left := Checkbox1.Left + Checkbox1.Width + 5;
  finally
    bmp.Free;
  end;
end;

Karena tombol tidak memiliki kotak apa pun, jadi saya menggunakan size.cx daripada menambahkan beberapa nilai. Namun, dalam pengujian saya, sebenarnya lebar teks tidak benar, yang membuat tombol tidak dapat memenuhi keseluruhan teks, lihat di bawah:

Jawaban

2 AndreasRejbrand Jan 15 2021 at 21:20

Ini dua sen saya.

Untuk mendapatkan ukuran kotak centang yang sebenarnya, saya yakin Anda harus menanyakan API tema Win32 ( uses UxTheme):

var
  h: HTHEME;
  S: TSize;
begin

  h := OpenThemeData(Handle, 'BUTTON');
  try

    if Succeeded(GetThemePartSize(h, Canvas.Handle, BP_CHECKBOX,
      CBS_UNCHECKEDNORMAL, nil, TS_DRAW, S))
    then
      ShowMessage('Check box width: ' + S.cx.ToString);

  finally
    CloseThemeData(h);
  end;

Demikian pula, ini mengambil lebar teks (caption):

var
  h: HTHEME;
  R: TRect;
begin

  h := OpenThemeData(Handle, 'BUTTON');
  try

    if Succeeded(GetThemeTextExtent(h, Canvas.Handle, BP_CHECKBOX,
      CBS_UNCHECKEDNORMAL, PChar(CheckBox1.Caption),
      Length(CheckBox1.Caption), 0, nil, R))
    then
      ShowMessage('Caption width: ' + R.Width.ToString);

  finally
    CloseThemeData(h);
  end;

Apa yang tetap tidak diketahui adalah padding antara kotak centang dan keterangan. Saya tidak tahu cara yang benar untuk mendapatkan ini, tetapi sepertinya ini paling sering sama dengan lebar spasi:

var
  h: HTHEME;
  S: TSize;
  R: TRect;
begin

  h := OpenThemeData(Handle, 'BUTTON');
  try

    if Succeeded(GetThemePartSize(h, Canvas.Handle, BP_CHECKBOX,
      CBS_UNCHECKEDNORMAL, nil, TS_DRAW, S))
    then
      ShowMessage('Check box width: ' + S.cx.ToString);

    if Succeeded(GetThemeTextExtent(h, Canvas.Handle, BP_CHECKBOX,
      CBS_UNCHECKEDNORMAL, PChar(#32+CheckBox1.Caption),
      1+Length(CheckBox1.Caption), 0, nil, R))
    then
      ShowMessage('Caption width including padding: ' + R.Width.ToString);

  finally
    CloseThemeData(h);
  end;