Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "Компоненты";
Текущий архив: 2007.08.19;
Скачать: [xml.tar.bz2];

Вниз

TCollection. run-time VS desine-time   Найти похожие ветки 

 
DevilDevil ©   (2006-09-26 14:32) [0]

Программирую таблицу. Есть свойство ColsCount - количество столбцов. Каждому столбцу в таблице соответствует класс TCol.

Теобходимо написать редактор столбцов.

Для реализации этого свойства [Columns ...] использую коллекцию. Мне не хочется наследовать уже готовый TCol от TCollectionItem. Поэтому я реализую "соответствие"; в моём классе-элементе коллекции в разделе public содержится свойство Column : TCol.

При изменении количества столбцов (свойства ColsCount) соответствующим образом должна изменяться коллекция:

void __fastcall TInfoTable::SetColsCount(int Count)
{
...>
Если, например, было 0</B, а стало Count [1</B например]
if (Count > FColsCount)
{
FCols.Count = Count;

for (int i = FColsCount; i < Count; i++)
{
TCol *Buf = new TCol(this);
FCols.Memory[i] = Buf;
// -->>>
FColumns->Add()->Column = Buf;
}
}
...


Так всё вроде нормально работает (кроме случаев удаления элементов коллекции в дизайнере).

Стал добавлять свойства в мой TColumnItem - потомок TCollectionItem; в частности свойство Title : string; :

void __fastcall TColumnItem::SetTitle(AnsiString S)
{
 FCol->Title = S;
}


И так всё работает [в desine-time]. Зато при запуске приложения в ран-тайм, ошибка доступа к данным. Начал трассировать, оказывается, FCol = nil. Начал трассировать дальше, оказалась вообще ерунда какая-то...  TColumnItem сначала создаётся, потом даже вызывается его деструктор, потом...

Очень прошу помощи. Что я делаю не так?


 
DevilDevil ©   (2006-09-26 14:35) [1]

sorry за опечатку в тегах


 
DimaBr   (2006-09-26 15:11) [2]

не видно конструктора и описания класса.
1. что раньше - создаётся коллекция или назначаютсяколичество столбцов ?
2. что раньше в published  Column или ColsCount ?

> Теобходимо написать редактор столбцов.

?????


 
DevilDevil ©   (2006-09-26 15:18) [3]

> Теобходимо написать редактор столбцов.
?????


Необходимо иметь возможность в дизайн-тайм изменять Title, Width и др свойства столбца.

> 1. что раньше - создаётся коллекция или назначаются количество  столбцов ?

конструктор коллекции выполняется в конструкторе таблицы. Количество столбцов назначается... при изменении published свойства Таблица.ColsCount

> 2. что раньше в published  Column или ColsCount ?
ColsCount


 
DimaBr   (2006-09-26 16:24) [4]


> Необходимо иметь возможность в дизайн-тайм изменять Title,
>  Width и др свойства столбца.

Для этого достаточно иметь published свойтство типа TCollection, тогда в инспекторе у этого свойства появится "..." с окном для редактирования коллекции. Если вы хотите изменять ReadOnly свойство ColCount, то я бы написал так

   fColumns: TCollection;
   property Columns: TCollection read fColumns write fColumns;
   property ColCount: integer read GetColCount write SetColCount;

function TForm1.GetColCount: integer;
begin
 Result := fColumns.Count;
end;

procedure TForm1.SetColCount(const Value: integer);
begin
 while ColCount < Value do Columns.Add;
 while ColCount > Value do Columns.Delete(ColCount-1);
end;


 
DevilDevil ©   (2006-09-27 15:33) [5]

В приведённом тобой случае, что сохраниться в dfm и в каком порядке будет работать?


 
DimaBr   (2006-09-27 15:46) [6]


private
fColumns: TCollection;
published
  property Columns: TCollection read fColumns write fColumns;
  property ColCount: integer read GetColCount write SetColCount;

и не  дай бог наоборот


 
DevilDevil ©   (2006-09-27 15:49) [7]

А почему "write fColumns" а не SetColumns?


 
DimaBr   (2006-09-27 16:05) [8]

Можно и SetColumns


 
DevilDevil ©   (2006-09-27 16:14) [9]

непонятно. Чтобы все столбцы загрузились (т.е. были созданы, инициализированы свойства Width и Title) ищз dfm, вроде необходимо использовать TCollection.Assign() .

Недопонимаю... Недопонимаю.......


 
DimaBr   (2006-09-27 16:19) [10]

Попробуйте оба варианта, потом расскажете где собака порылась.


 
DevilDevil ©   (2006-09-27 16:29) [11]

мммм.....

Что и в какой последовательности должно следовать, чтобы все столбцы создались и инициализировались, чтобы свойство ColsCount тоже работало?

В каких случаях следует использовать, а в каких нет SomeObject.Assign() ? Чё то я запутался уже...


 
DevilDevil ©   (2006-09-27 17:19) [12]

Разве может быть такое???

У коллекции перекрываю методы Add и Delete, в которых вписываю ShowMessage() с аргументами "Add" и "Delete" соответственно. При добавлении и удалении элементов коллекции в дизайнере, никаких ShowMessage не вызывается. Из-за чего такое происходит?

P.S. Компонент перекомпилирован


 
DevilDevil ©   (2006-09-27 18:23) [13]

Когда коллекция грузится из dfm, она вызывает метод Add? Если да, то свойство ColsCount сохранять не надо - т.к. оно само примет нужное значение при загрузке dfm.


 
DimaBr   (2006-09-28 08:47) [14]


> У коллекции перекрываю методы Add и Delete,

Методы не виртуальны, как вы умудрились их перекрыть ?

> свойство ColsCount сохранять не надо

В принципе правильно.


 
DevilDevil ©   (2006-09-28 15:22) [15]

> DimaBr   (28.09.06 08:47) [14]
> Методы не виртуальны, как вы умудрились их перекрыть ?


ммм... в Си нет директивы override, там это делается автоматически (если естественно метод виртуальный).

А как тогда мне перехватить и правильно отреагировать на изменения коллекции в дизайнере?

P.S. Дима, во - первых мы с Вами тёски, во - вторых Вы может быть старше меня... Может всё таки на "ты" ? :)


 
DimaBr   (2006-09-28 15:32) [16]

В коллекции есть методы

procedure Update(Item: TCollectionItem); virtual; //
procedure Added(var Item: TCollectionItem); virtual; deprecated;
procedure Deleting(Item: TCollectionItem); virtual; deprecated;
procedure Notify(Item: TCollectionItem; Action: TCollectionNotification); virtual;

которые и можно перекрыть


 
DimaBr   (2006-09-28 15:36) [17]

То есть пишем свою коллекцию

TMyCollection = class(TOwnedCollection)
  protected
     procedure Update(Item: TCollectionItem);override;        
end;

procedure TMyCollection.Update(Item: TCollectionItem);
begin // возникает при изменении элемента коллекции в инспекторе

end;

и тогда
fColumns := TMyCollection.Create(self,TMyCollectionItem);


 
DevilDevil ©   (2006-09-28 16:45) [18]

перекрываю метод Added, вписываю ShowMessage("Added");

Достаточно странно: при добавлении, ShowMessage вызывается дважды. Аналогично в Ран-Тайм; при загрузке приложения, на три колонки - 6 вызовов  ShowMessage. Почему?

Как отследить, присвоено свойство при загрузке dfm или нет?

Позорный вопрос: за что отвечает директива deprecated ?


 
Ketmar ©   (2006-09-28 16:51) [19]

"deprecated" -- "устаревшее".


 
DimaBr   (2006-09-28 16:56) [20]


> Как отследить, присвоено свойство при загрузке dfm или нет?

не понял

deprecated - говорит о том, что использованая функция объявлена как устаревшая и рекомендуется использовать что-то новое


 
DevilDevil ©   (2006-09-28 17:50) [21]

> Как отследить, присвоено свойство при загрузке dfm или нет?
> не понял

Ну смотри. При вызове Added я должен произвести некоторые действия с оперативной памятью, добавить столбец, перерисовать таблицу.

Незнаю почему [ :) ], но мне не хочется перерисовывать таблицу, если свойство присвоено (или вызван метод, Added, например) в момент загрузки dfm. Таких загрузок много. На данный момент выполняется минимум 27 лишних перерисовок таблицы.

Почему метод Added дублируется?


 
DevilDevil ©   (2006-09-28 20:15) [22]

АААЛЕЕЕЛУУУЯЯ, ААЛЕЛУУУУЯ, АЛЕЕЕЕЛУЯ, АЛЕЛУЯ, АЛЕЛУЯ...

TCollection.Notify:

begin

  case
(Action) of:

    cnAdded     : MyAdding(Item);
    cnExtracting, cnDeleting  : MyDeleting(Item->Index);

  end;

end;


...таким банальным образом отлавливаю события добавления и удаления ...


 
DimaBr   (2006-09-29 08:48) [23]

Для уменьшения количества отрисовок используем BeginUpdate - EndUpdate


 
DevilDevil ©   (2006-10-02 15:46) [24]

Снова вопросы.

Создал пока 2 свойства: Title : string и Width : integer;

Примечательно то, что если изменить эти своства в Object Inspector-е, то всё корректно сохранится в dfm. Если Object Inspector не использовать, то свойство не сохраняется.

Допустим ширина первого столбца равна 20 пикселей. Мышью изменяю ширину столбца до ста двадцати пикселей, запускаю - ширина почему-то равна 20 пикселей. Смотрю в Object Inspector; написано 120. Запускаю - опять 20. Опять захожу в Инспектор, кликаю в поле Width, нажимаю Enter, запускаю... Всё работает правильно...

Вопрос: Как заставить сохраниться в dfm?

Вопрос №2: При клике в шапке столбца, соответсвующий столбец должен открыться в Инспекторе Объектов. Как это реализовать?


 
DimaBr   (2006-10-02 16:20) [25]

1. Нужно сообщить дизайнеру что произошли изменения.

при перемещении колонки
if GetParentForm(self) > nil then
 if GetParentForm(self).Designer <> nil then
   GetParentForm(self).Designer.Modified;

2. Для этого вам придётся переписать половину VCL, по крайней мере свой ТСомponent, TControl и т д. Это реализовано в DevExpress, загляните.


 
DevilDevil ©   (2006-10-02 18:05) [26]

ВСЕМ спасибо ОГРОМНОЕ. В частности ДимеБр !!!

Вроде всё работает как надо...



Страницы: 1 вся ветка

Форум: "Компоненты";
Текущий архив: 2007.08.19;
Скачать: [xml.tar.bz2];

Наверх




Память: 0.52 MB
Время: 0.041 c
15-1184961545
Bogdan1024
2007-07-20 23:59
2007.08.19
Интернет-провайдеры в Киеве


15-1185169315
gosean
2007-07-23 09:41
2007.08.19
Приветствие


2-1185617304
vegarulez
2007-07-28 14:08
2007.08.19
Как сделать выравнивание Caption в Button`e alLeft вместо центра


2-1185141282
Альберт
2007-07-23 01:54
2007.08.19
Проверка на существование файла или директории


2-1184900752
vegarulez
2007-07-20 07:05
2007.08.19
Вопрос: Как привязать процедуру (click) к созданной кнопке?





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский