Форум: "Основная";
Текущий архив: 2007.11.11;
Скачать: [xml.tar.bz2];
ВнизПроблемы отрисовки TComboBox в режиме OwnerDrawVariable Найти похожие ветки
← →
Tack © (2007-06-29 17:46) [0]Есть комбобокс, при раскрытии которого надо отрисовать 3 цветастеньких итема, каждый с разной высотой. Включаю режим OwnerDrawVariable, пишу обработчики OnMeasureItem, OnDrawItem. Все рисуется и рассчитывается, как надо, НО:
1) При свойствах
ItemHeight = 16; // стояло по умолчанию
DropDownCount = 3;
комбобокс не выпадает (выпадает полоска в 2 пикс.)
2) При свойствах
ItemHeight = 32;
DropDownCount = 64;
комбобокс выпадает и показывает 1 итем (по высоте первого), остальные надо прокручивать
3) При свойствах
ItemHeight = 100;
DropDownCount = 100;
список вываливается на фиксированную высоту, меньшую чем надо для отображения всех трех элементов. Опять появляется прокрутка.
Требуется, чтобы все три элемента выпали в список без прокрутки. Там где-то 300 пикселей по вертикали всего.
Числа ставил просто от фонаря, т.к. не могу вкурить, как они коррелируют.
Может, у кого-то была подобная проблема? Подскажите решение, пожалуйста.
← →
Tack © (2007-06-29 20:02) [1]вот пример кода, можете у себя запустить. Может это GDI у меня плохая, я уже не знаю что еще придумать:
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls;
type
TForm1 = class(TForm)
ComboBox: TComboBox;
procedure ComboBoxMeasureItem(Control: TWinControl; Index: Integer;
var Height: Integer);
procedure ComboBoxDrawItem(Control: TWinControl; Index: Integer;
Rect: TRect; State: TOwnerDrawState);
procedure FormCreate(Sender: TObject);
end;
var
Form1: TForm1;
implementation
{$R *.dfm}
procedure TForm1.ComboBoxMeasureItem(Control: TWinControl; Index: Integer;
var Height: Integer);
begin
// Рабочий вариант высот
// case Index of
// -1: Height := 16;
// 0: Height := 62;
// 1: Height := 75;
// 2: Height := 49;
// end;
// Нерабочий вариант высот
case Index of
-1: Height := 16;
0: Height := 62;
1: Height := 75;
2: Height := 62;
end;
end;
procedure TForm1.ComboBoxDrawItem(Control: TWinControl; Index: Integer;
Rect: TRect; State: TOwnerDrawState);
var
rc: TRect;
begin
ComboBox.Canvas.FillRect(Rect);
rc := Rect;
InflateRect(rc, -3, -3);
if not (odComboBoxEdit in State) then
begin
if odSelected in State then
begin
ComboBox.Canvas.Pen.Color := clRed;
ComboBox.Canvas.Pen.Width := 3;
ComboBox.Canvas.Rectangle(rc);
ComboBox.Canvas.MoveTo(rc.Left, rc.Top);
ComboBox.Canvas.LineTo(rc.Right, rc.Bottom);
ComboBox.Canvas.MoveTo(rc.Left, rc.Bottom);
ComboBox.Canvas.LineTo(rc.Right, rc.Top);
end
else
begin
ComboBox.Canvas.Pen.Color := clBlue;
ComboBox.Canvas.Pen.Width := 3;
ComboBox.Canvas.Rectangle(rc);
ComboBox.Canvas.MoveTo(rc.Left, rc.Top);
ComboBox.Canvas.LineTo(rc.Right, rc.Bottom);
ComboBox.Canvas.MoveTo(rc.Left, rc.Bottom);
ComboBox.Canvas.LineTo(rc.Right, rc.Top);
end
end
else
ComboBox.Canvas.TextOut(10, 4, "blablabla");
end;
procedure TForm1.FormCreate(Sender: TObject);
begin
ComboBox.Width := 250;
ComboBox.Style := csOwnerDrawVariable;
ComboBox.ItemHeight := 62; /// Если эту строку убрать, то список не выпадает
ComboBox.DropDownCount := 3; // Если здесь поставить другие числа, то эффекта никакого
end;
end.
← →
lottis (2007-08-21 17:11) [2]ты ItemHeight = 16; - оставь по умолчанию
а DropDownCount = 20; поставь 20. и всё прокатит.. :-)
← →
Tack © (2007-08-21 22:42) [3]> [2] lottis (21.08.07 17:11)
> ты ItemHeight = 16; - оставь по умолчанию
> а DropDownCount = 20; поставь 20. и всё прокатит.. :-)
Попробовал, с нерабочим вариантом высот все равно появляется прокрутка :-(
← →
Leonid Troyanovsky © (2007-08-23 12:06) [4]
> Tack © (21.08.07 22:42) [3]
> Попробовал, с нерабочим вариантом высот все равно появляется
> прокрутка :-(
В борландовской реализации AdjustDropDown косяк:
не учиывается, что при csOwnerDrawVariable высота итемов разная.
Т.е., надо сделать наследника с примерно таким методом
procedure TMyComboBox.AdjustDropDown; // override;
var
AHeight : Integer;
begin
FDroppingDown := True;
AHeight := .. ; // вычисляем требуемую высоту вып. списка
SetWindowPos(FDropHandle, 0, 0, 0, Width, AHeight, SWP_NOMOVE or SWP_NOZORDER or SWP_NOACTIVATE or SWP_NOREDRAW or SWP_HIDEWINDOW);
FdroppingDown := False;
SetWindowPos(FDropHandle, 0, 0, 0, 0, 0, SWP_NOMOVE or SWP_NOSIZE or
SWP_NOZORDER or SWP_NOACTIVATE or SWP_NOREDRAW or SWP_SHOWWINDOW);
end;
Но, скорее всего, больше чем на полувысоту экрана сделать его не дадут.
Если видна хотя бы часть последнего итема, то можно отказаться
от скролбара, перекрыв CreateParams:
inherited;
params := params and not CBS_NOINTEGRALHEIGHT and not WS_VSCROLL;
--
Regards, LVT.
← →
Tack © (2007-08-26 12:04) [5]Леонид, спасибо огромное!
Страницы: 1 вся ветка
Форум: "Основная";
Текущий архив: 2007.11.11;
Скачать: [xml.tar.bz2];
Память: 0.47 MB
Время: 0.051 c