Форум: "Основная";
Текущий архив: 2002.04.22;
Скачать: [xml.tar.bz2];
Внизпередача объектов из dll в вызыващщее приложение Найти похожие ветки
← →
d_oleg (2002-04-09 11:44) [0]А кто-нибудь имел опыт по созданию компонентов в dll, но указывая в качестве родителя компонент вызывающего приложения?
У меня такая ситуация - грубо есть форма основного приложения, на которой после подгрузки dll нужно отобразть, скажем, checkbox. После выгрузки, естесственно, удалть.
← →
Alx2 (2002-04-09 11:58) [1]Скорее всего, в DLL нужно будет передавать контекст Application и Screen
← →
Виктор Щербаков (2002-04-09 12:09) [2]Если, к примеру, приложение выделяет память для объекта, а dll её освобождает, то нужно пользоваться общим менеджером памяти (т.е. ShareMem писать в Uses и таскать с собой Борландовскую dll). Но лучше всё же пакетами пользоваться, там таких проблем нет.
← →
d_oleg (2002-04-09 12:18) [3]дык ShareMem использую, передаю в dll объект, который хочу родителем сделать, в dll создаю контрол, всё работает классно, потом когда dll выгружаю - прибиваю созданный объект через free. И после этого в вызыв. приложении начинаются страхи...
← →
Игорь Шевченко (2002-04-09 12:24) [4]День добрый,
Чтобы страхов не было, используйте логический признак, если DLL загружена и отображайте CheckBox в основном приложении, тогда и страхов не будет.
Остальное не пройдет. RTFS: Controls.FindControl
С уважением,
← →
Alx2 (2002-04-09 12:24) [5]Скорее всего, в DLL нужно будет передавать контекст Application и Screen
← →
d_oleg (2002-04-09 13:49) [6]Ну а смысл тогда библиотеку подгружать? Смысл-то в том, что передаётся в-общем-то неизвестный контрол, поведение которого как раз в библиотеке и описано.
← →
Игорь Шевченко (2002-04-09 13:53) [7]День добрый, d_oleg,
Нельзя (в общем случае), работать с Control, который не описан в основном приложении, тем более, вставлять его в форму основного приложения.
С уважением,
← →
Alx2 (2002-04-09 14:06) [8]>d_oleg (09.04.02 13:49)
>Смысл-то в том, что передаётся в-общем-то неизвестный контрол,
>поведение которого как раз в библиотеке и описано.
Пусть поведение описано в DLL, но при реализации поведения должны использоваться глобальные объекты хоста, а не глобальные объекты DLL.
← →
d_oleg (2002-04-09 14:35) [9]Ну в-общем работает всё. Причём вот собственно каким образом: после загрузки dll в неё передаётся объект-родитель подгружаемых объектов (AObject). В dll создаются необходимые объекты, затем делается AObject.InsertObject для каждого созданного объекта. А теперь _ДЕТАЛЬ_: если при выгрузке dll пытаться убить эти объекты в dll, как учит Borland - всё порушится нафик. И напротив, если делать так как Borland говорит, что ни в коем случае нельзя, а именно уничтожать эти объекты из вызывающего приложения, - всё прекрасно работает.
← →
Alx2 (2002-04-09 14:46) [10]А DLL через LoadLirary грузится?
Если нет, то все, кажется, объяснимо.
Если да, то в какой момент FreeLibrary вызывается?
← →
Alx2 (2002-04-09 14:52) [11]>В dll создаются необходимые объекты, затем ...
Как создаются, можно код?
← →
d_oleg (2002-04-09 14:57) [12]Грузится именно так. FreeLibrary вызывается в самый посл. момент, когда всё уже прибито.
Объекты создаются совершенно стандартно. Ну вот кусок кода:
FSearchWndExt := TSearchWndExt.Create(nil);
ASearchWnd.InsertComponent(FSearchWndExt);
With FSearchWndExt do
begin
ParentFont := False;
Parent := ASearchWnd;
...
end;
ASearchWnd передаётся с хоста. FSearchWndExt - потомок TGroupBox c набором компонентов.
← →
Alx2 (2002-04-09 15:13) [13]Я сейчас полазил по коду. При создании/разрушении объектов используется в DLL используется DLL-овский Application и Screen.
Они отличаются от Application и Screen хоста.
Попробуй все-таки переприсвоить в DLL его родные Application и Screen на соответствующие объекты хоста.
Вот запчасть из DLL:
Var
SaveApp: TApplication;
SaveScr: TScreen;
{$R *.RES}
Procedure RestoreAppContext; Stdcall;
Begin
If SaveApp <> Nil Then
Application := SaveApp;
If SaveScr <> Nil Then
SCREEN := SaveScr
End;
procedure InitAppContext(App: TApplication; Scr: TScreen); Stdcall;
Begin
If SaveApp = Nil
Then SaveApp := Application;
If SaveScr = Nil
Then SaveScr := SCREEN;
Application := App;
Screen := Scr;
End;
Begin
SaveApp := Nil;
SaveScr := Nil;
End.
← →
Alx2 (2002-04-09 15:19) [14]Перед первым использованием DLL (но когда уже созданы Application и Screen) вызываем из нее InitAppContext(Application, Screen). Когда все народившееся в DLL прибито вызываем из DLL RestoreAppContext;
← →
d_oleg (2002-04-09 15:21) [15]нафига? и так же всё работает?
И потом, когда-то давно ещё под 4 делф. я так и делал, то есть в проекте вызывал фору из dll: сразу после загр. dll присваивал Appl., перед выгрузкой восстанавливал. Но под D6 так не проходит, если делать так,основное приложение после выгрузки dll "исчезает" с экрана, приходится с таскбара его снова ввбирать. Это не есть хорошо.
Страницы: 1 вся ветка
Форум: "Основная";
Текущий архив: 2002.04.22;
Скачать: [xml.tar.bz2];
Память: 0.48 MB
Время: 0.006 c