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

Вниз

Как всегда наступил на грабли под названием AV В чем тут ошибка?   Найти похожие ветки 

 
paul_k ©   (2005-07-11 16:33) [0]

Как всегда наступил на грабли под названием  AV В чем тут ошибка, кроме моих кривых рук? Разъясните плиз подробнее, чтоб больше не спотыкатся

procedure TForm1.ChangePickCombo(Sender: TObject);
begin
   ShowMessage(TComboBox(Sender).ClassName);
   Sender.Destroy;
end;

procedure TForm1.ToolButton6Click(Sender: TObject);
Var
CbBox : TComboBox;
begin
   CbBox := TComboBox.Create(nil);
   CbBox.Parent:=m_sql;
   CbBox.Left := m_sql.Left+20;
   CbBox.Top := m_sql.top+1;
   CbBox.OnChange := Form1.ChangePickCombo;
   CbBox.Items.Add("11");
   CbBox.Items.Add("12");
end;


 
begin...end ©   (2005-07-11 16:36) [1]

> paul_k ©   (11.07.05 16:33)
> В чем тут ошибка, кроме моих кривых рук?

В уничтожении объекта в обработчике его события.


 
paul_k ©   (2005-07-11 16:45) [2]

begin...end ©   (11.07.05 16:36) [1]
Понятно. Как тогда надо поступить? Должна же быть методика соответствующая
- по кнопке (сочетание клавиш) отображается объект (комбобокс)
- после выбора записи в комбобоксе используется текст выбранный и комбобокс больше не нужен, следовательно есть желание его изничтожить


 
jack128 ©   (2005-07-11 16:46) [3]

Через PostMessage послать форме какое нить сообщение и в обработчике этого сообщения уничтожить комбобокс. Пример - см TCustomForm.Release - там форма вообще сама себя уничтожает.


 
begin...end ©   (2005-07-11 16:50) [4]

> paul_k ©   (11.07.05 16:45) [2]

Если нужно уничтожить объект именно из обработчика его события, можно определить собственное сообщение, которое и посылать форме (с помощью PostMessage) из обработчика события компонента. В методе формы -- обработчике этого сообщения -- уже можно будет уничтожить компонент. Вот пример:

const
 WM_DESTROYOBJECT = WM_USER + 100;

type
 TForm1 = class(...)
 ...
 private
   procedure WMDestroyComboBox(var Message: TMessage); message WM_DESTROYOBJECT;
 end;

procedure TForm1.WMDestroyComboBox(var Message: TMessage);
begin
 // В Message.WParam пришёл указатель на экземпляр объекта. Вызываем Free:
 TObject(Message.WParam).Free
end;

procedure TForm1.ChangePickCombo(Sender: TObject);
begin
 ShowMessage(TComboBox(Sender).ClassName);
 // Посылаем форме сообщение, передавая Sender в параметре WParam
 PostMessage(Self.Handle, WM_DESTROYCOMPONENT, Integer(Sender), 0)
end.


 
begin...end ©   (2005-07-11 16:51) [5]

Сорри, в строке с PostMessage WM_DESTROYCOMPONENT нужно заменить на WM_DESTROYOBJECT.


 
paul_k ©   (2005-07-11 16:54) [6]

begin...end ©   (11.07.05 16:50) [4]
Методика понятна.
Смущает только следующее
WM_DESTROYOBJECT = WM_USER + 100
почему не +1, или просто =1?


 
jack128 ©   (2005-07-11 16:58) [7]

paul_k ©   (11.07.05 16:54) [6]
потому что все собщения <= WM_USER зарезервированы Windows для своих целей(хотя вот нарпимер борланд чихать хотел на эти рекомендации MS ;) )  а следующие 100 сообщений используются в Common Controls, если не ошибаюсь. Так как форма - НЕ Common Control, то можно было бы и WM_USER + 1 использовать, но зачем искушать судьбу? ;)


 
paul_k ©   (2005-07-11 17:00) [8]

jack128 ©   (11.07.05 16:58) [7]
понял.. то есть если я объявляю константы свои для сообщений то корректно начитнать их с +100 и более так?


 
begin...end ©   (2005-07-11 17:01) [9]

> paul_k ©   (11.07.05 16:54) [6]

WM_USER + 1 -- в принципе, можно, но нежелательно. Просто 1 -- нельзя (1 попадает в диапазон сообщений, зарезервированных Windows). Обычно нижней допустимой границей для значений идентификаторов сообщений считают именно WM_USER + 100.

The WM_USER constant is used to distinguish between message values that are reserved for use by Windows and values that can be used by an application to send messages within a private window class. There are five ranges of message numbers:

Range                 Meaning
0 through WM_USER - 1 Messages reserved for use by Windows.
WM_USER through 0x7FFF Integer messages for use by private window classes.
0x8000 through 0xBFFF Messages reserved for future use by Windows.
0xC000 through 0xFFFF String messages for use by applications.
Greater than 0xFFFF Reserved by Windows for future use.


 
paul_k ©   (2005-07-11 17:04) [10]

Спасибо, вроде некоторое понимание наступило


 
jack128 ©   (2005-07-11 17:08) [11]

paul_k ©   (11.07.05 17:00) [8]
то корректно начитнать их с +100 и более так?

для твоего случая - да.
В общем случае (критично для окон верхнего уровня, в VCL приложении - это Application.Handle) желательно ID сообщений получать используя функцию RegisterWindowMessage. Но в твоем случае - это излишне..



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

Форум: "Основная";
Текущий архив: 2005.07.31;
Скачать: [xml.tar.bz2];

Наверх




Память: 0.47 MB
Время: 0.038 c
1-1121297550
JohnSmith
2005-07-14 03:32
2005.07.31
Как создать динамический массив потоков ?


10-1098423704
Patrick
2004-10-22 09:41
2005.07.31
Экспорт в Excel


3-1118750598
__oleg
2005-06-14 16:03
2005.07.31
Починка БД Firebird


4-1117652570
Ralf
2005-06-01 23:02
2005.07.31
UpdateLayeredWindow


14-1121016654
-=}{eRsOn=-
2005-07-10 21:30
2005.07.31
D6 или D7 ...





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
Английский Французский Немецкий Итальянский Португальский Русский Испанский