Форум: "Основная";
Поиск по всему сайту: delphimaster.net;
Текущий архив: 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 "исчезает" с экрана, приходится с таскбара его снова ввбирать. Это не есть хорошо.




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




Наверх





Память: 0.74 MB
Время: 0.03 c
1-69809           MystiX                2002-04-09 18:31  2002.04.22  
Help with mouse


3-69735           Ежик                  2002-04-01 13:30  2002.04.22  
Как програмно посчитать кол-во записей в БД?


1-69818           ice                   2002-04-08 21:21  2002.04.22  
Поиск файлов по ftp


3-69744           vasilly               2002-04-01 08:43  2002.04.22  
Нельзя сохранить из дельф больше чем 256 символов в MS SQL!!!


1-69918           ymin                  2002-04-09 11:28  2002.04.22  
А как сделать, чтобы Button была выделена и при нажатии Enter