![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
Многострочный текст в CheckListBox [D6, XP]
Pavelkq © (2008-02-21 12:52:00)По аналогии с многострочным ListBox-ом без проблем вывел много строк в CheckListBox, но каждая из них с маркером выделения. А мне надо, чтобы на все несколько строк был одн маркер. Естественно, что количество строк каждого элемента может быть разным, в зависимости от наполнения. (т.е. один элемент чеклистбокса - это несколько строк текста).
Пробовал копать в сторону рисования в листбоксе. Рисунок выводится, а текст - нет. Может, я как-то неверно управляю объектами? Хотел вместо объекта типа TBitmap запихать TMemo.
procedure TForm1.CheckListBox3DrawItem(Control: TWinControl;
Index: Integer; Rect: TRect; State: TOwnerDrawState);
var
MyMemo: TMemo;
Offset: Integer;
BMPRect: TRect;
begin
with (Control as TCheckListBox).Canvas do
begin
FillRect(Rect);
MyMemo := TMemo.Create(CheckListBox3);
MyMemo.Text:='fgsdf sdfg sfg sdfg s dfgsdf f gnsf h345245 fg w y 356y2345e v45t24';
Offset := 0;
if MyMemo <> nil then
begin
BMPRect := Bounds(Rect.Left+2, Rect.Top+2,
(Rect.Bottom-Rect.Top-2)*2, Rect.Bottom-Rect.Top-2);
{StretchDraw(BMPRect, Bitmap); Можно просто нарисовать, но лучше сначала убрать фон}
// BrushCopy(BMPRect,MyMemo, Bounds(0, 0, Bitmap.Width, Bitmap.Height),
// MyMemo.Canvas.Pixels[0, Bitmap.Height-1]);
Offset := (Rect.Bottom-Rect.Top+1)*2;
end;
TextOut(Rect.Left+Offset, Rect.Top, CheckListBox3.Items[index]);
MyMemo.Free;
end;
end;
Как это сделать?
clickmaker (2008-03-03 14:20:00) [1]
> при значении длинны -1 строка должна быть с нулевым символом
> в конце. А какая она там на самом деле - фиг ее знает
а с чего бы ей не быть с нулевым символом в конце?
DiamondShark (2008-03-03 13:35:00) [2]
> Не подскажите ли, как это можно исправить?
Очень просто: при расчёте высоты текста учитывать размер "галочки". В приведённом коде этого нет.
> length(CheckListBox3.Items[Index])+6
бред сивой кобылы.
Совсем недавно был точно такой же вопрос. Там привели полностью готовый код.
Pavelkq (2008-03-03 12:35:00) [3]Я сам нашел выход:
DrawText(Canvas.Handle, PChar(Items[Index]), length(CheckListBox3.Items[Index])+6, R, DT_WORDBREAK or DT_CALCRECT);
6 - это опытным путем подобранное число. Меньше него все равно обрезает. протестил на паре десятков предложений. Работает хорошо. Очевидно это связано с тем, что при значении длинны -1 строка должна быть с нулевым символом в конце. А какая она там на самом деле - фиг ее знает.
Washington (2008-03-03 10:40:00) [4]О, а я уже задавал недавно такой вопрос :)
Pavelkq (2008-03-03 09:51:00) [5]
> {RASkov} © (21.02.08 17:44) [9]
Обнаружился глюк. Вывожу в чеклистбокс предложение, а оно отображается не полностью (последние 1-3 слова исчезают). Хотя, если проверить содержимое элемента программно, то там все есть.
Например, вывожу предложение : "Во всех космических амплитудах будет краеугольным основанием мысль, она может изменять карму, она может решать сроки, она открывает врата и может закрыть их."
В результате получаю: "Во всех космических амплитудах будет краеугольным основанием мысль, она может изменять карму, она может решать сроки, она открывает врата и может"
Не подскажите ли, как это можно исправить?
Pavelkq (2008-02-22 08:53:00) [6]Заработало при установленном CheckListBox1.Style:=lbOwnerDrawVariable;
В справке сказано, что OnMeasureItem возникает только при этом значении стиля.
Очень здорово получились переносы строк!
Огромное спасибо!
{RASkov} (2008-02-21 17:44:00) [7]> [8] Pavelkq (21.02.08 14:47)
procedure TForm1.CheckListBox1MeasureItem(Control: TWinControl; Index: Integer; var Height: Integer);
var R: TRect;
begin
R:=CheckListBox1.ItemRect(Index);
with TCheckListBox(Control) do
DrawText(Canvas.Handle, PChar(Items[Index]), -1, R, DT_WORDBREAK or DT_CALCRECT);
Height:=R.Bottom-R.Top;
end;
procedure TForm1.CheckListBox1DrawItem(Control: TWinControl;
Index: Integer; Rect: TRect; State: TOwnerDrawState);
begin
with Control as TCheckListBox, Canvas do begin
FillRect(Rect);
DrawText(Handle, PChar(Items[Index]), -1, Rect, DT_WORDBREAK);
end;
end;
Pavelkq (2008-02-21 14:47:00) [8]Извините, возможно я действительно некорректно высказался. Перефразирую: Как задавать разные значения Height для каждой строки в CheckListBox?
Johnmen (2008-02-21 14:37:00) [9]
> Хм, оказывается, высота строк не меняется в зависимости
> от содержимого. Один текст наползает на другой.
Ты жалуешься или претензии выдвигаешь?
Pavelkq (2008-02-21 14:33:00) [10]Хм, оказывается, высота строк не меняется в зависимости от содержимого. Один текст наползает на другой.
Pavelkq (2008-02-21 13:54:00) [11]Упс, нет, не ошибка. Это я чё-то напорол. Все верно в Вашем коде!
Еща наз спасибо!
Pavelkq (2008-02-21 13:52:00) [12]Ошибка там была маленькая. Еще точнее : CheckListBox3.OnMeasureItem:=CheckListBox1.OnMeasureItem;
{RASkov} (2008-02-21 13:41:00) [13]> [2] Pavelkq (21.02.08 13:38)
Это что там за точка, окуда она!?
:)
Pavelkq (2008-02-21 13:38:00) [14]Ух ты! Заработало (CheckListBox1.OnMeasureItem:=CheckListBox1.MeasureItem;)!
Спасибо!
{RASkov} (2008-02-21 13:14:00) [15]> [0] Pavelkq (21.02.08 12:52)
procedure TForm1.FormCreate(Sender: TObject);
var N: Integer;
begin
CheckListBox1.OnMeasureItem:=CheckListBox1MeasureItem;
CheckListBox1.OnDrawItem:=CheckListBox1DrawItem;
CheckListBox1.Style:=lbOwnerDrawVariable;
for N:=0 to 9 do CheckListBox1.AddItem('String ?'+IntToStr(N), nil);
end;
procedure TForm1.CheckListBox1MeasureItem(Control: TWinControl;
Index: Integer; var Height: Integer);
begin
Height:=12 * ((Index mod 3)+1);
end;
procedure TForm1.CheckListBox1DrawItem(Control: TWinControl;
Index: Integer; Rect: TRect; State: TOwnerDrawState);
begin
with Control as TCheckListBox, Canvas do begin
FillRect(Rect);
TextOut(Rect.Left, Rect.Top, Items[Index]);
case Index mod 3 of
1: TextOut(Rect.Left, Rect.Top+12, 'Second string');
2: begin
TextOut(Rect.Left, Rect.Top+12, 'Second string');
TextOut(Rect.Left, Rect.Top+24, 'The third line');
end;
end;
end;
end;