|
| Тема: | Использование динамически загружаемых библиотек в Delphi |
| Автор | Сообщение |
|---|---|
![]() Рейтинг: 537 Темы: 13 Сообщения: 50 | Как загрузить библиотеку (dll) из приложения? |
![]() Рейтинг: 1340 Темы: 2 Сообщения: 17 | var LibHandle: THandle = 0; procedure TForm1.Button1Click(Sender: TObject);
begin
// загрузка библиотеки
LibHandle:= LoadLibrary('mylib.dll');
if LibHandle< 1 then
begin
ShowMessage(SysErrorMessage(GetLastError));
exit;
end
else
begin
// библиотека загружена успешно
end;
end;procedure TForm1.Button2Click(Sender: TObject);
begin
// выгрузка библиотеки
if LibHandle> 0 then
if not FreeLibrary(LibHandle) then
ShowMessage(SysErrorMessage(GetLastError));
end;При отсутствии файла будет выведено сообщение "Указанный модуль не найден" (или подобное). |
![]() Рейтинг: 537 Темы: 13 Сообщения: 50 | А как вызвать процедуру или функцию, расположенную в библиотеке? |
![]() Рейтинг: 1340 Темы: 2 Сообщения: 17 | Для вызова функции библиотеки необходимо, чтобы эта функция была объявлена как stdcall. Например объявим в библиотеке функцию: function MyFunction(Param1: Integer; Param2: String): Bool; stdcall; Чтобы вызвать эту функцию из приложения необходимо в этом приложении объявить класс, соответствующий этой функции: TMyFunction = function(Param1: Integer; Param2: String): Bool; stdcall; Непосредственно процедура вызова может выглядеть так: procedure TForm1.Button1Click(Sender: TObject);
var
CallMyFunction: TMyFunction;
Param1: Integer;
Param2: String;
ReturnResult: Boolean;
begin
// сначала надо загрузить библиотеку
// если загрузка выполнена, определяем адрес функции с именем MyFunction
// LibHandle – хендл, полученный при загрузке библиотеки
try
// определяем адрес функции MyFunction
@CallMyFunction:= GetProcAddress(LibHandle, 'MyFunction');
if @CallMyFunction<> nil then
begin
// если адрес функции MyFunction определен, продолжаем выполнение
// здесь или где-то ранее определим необходимые для функции параметры
Param1:= 1;
Param2:= 'my_string';
// вызываем функцию MyFunction
ReturnResult:= CallMyFunction(Param1, Param2);
// далее, если надо, обрабатываем возвращенный результат
end;
finally
// выгружаем библиотеку
end;
end;Конструкцию try..finally использовать необязательно. Можно обойтись проверкой необходимых условий с помощью оператора if. |
![]() Рейтинг: 537 Темы: 13 Сообщения: 50 | А как использовать dll со статической загрузкой? |
![]() Рейтинг: 1340 Темы: 2 Сообщения: 17 | Объявление функции/процедуры в dll не зависит от того, как будет загружаться библиотека. Например объявим функцию в dll: function MyFunction(Param1: Integer; Param2: String): Bool; stdcall; В вызывающем модуле: объявление функции, содержащейся в dll. function CallMyDllFunction(Param1: Integer; Param2: String): Bool; stdcall; external '(если надо, путь к dll)имя_ файла_dll’ name ‘MyFunction'; Можно использовать не имя, а индекс функции, но Microsoft объявила, что не будет в дальнейшем поддерживать вызов функций библиотек по индексу. Имена функций CallMyDllFunction и MyFunction могут совпадать. Это даже рекомендуется для удобства чтения кода. Вызов функции, содержащейся в dll. CallMyDllFunction(Param1, Param2); |
![]() Рейтинг: 537 Темы: 13 Сообщения: 50 | Вопрос на засыпку. Есть dll. В ней есть одна единственная форма и больше ничего, ни функций, ни других объектов. |
![]() Рейтинг: 537 Темы: 13 Сообщения: 50 | 1. Да, но могут остаться ссылки на пустые объекты. |
| Статистика форума |
|---|
| Сейчас эту тему читают: всего 1, пользователей 0, гостей 1 |
| Сообщений на форуме: 205 |
| Зарегистрировано пользователей: 2656 |
| Рекорд посещаемости: 411, зафиксирован 10 апрель 2017 13:47 |
