Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > IT форум > Помощь студентам
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 22.11.2010, 14:47   #1
eldalex
Пользователь
 
Регистрация: 01.09.2010
Сообщений: 52
По умолчанию Как вызвать функцию из Bpl если таковая имеется?

Всем доброго дня!
В общем в названии темы и вопрос. есть одна bpl, назовем её Mail.bpl.
она подключается к основному модулю и работает вполне хорошо. возникла необходимость создать еще одну bpl, назовем ее dop.bpl, которая будет дополнением main.bpl.
сейчас обе они готовы и работают, но есть одно но.
главный юнит dop.bpl просто указан в разделе uses у main.bpl т.е. при компиляции главного модуля он цепляет дополнительный и видит все его процедуры и функции.
проблема в том, что если запустить основную программу и не положить в папку dop.bpl то при подключении main.bpl происходит ошибка, что "модуль dop.bpl не найден, повторная установка приложения может решить эту проблему".
так вот. собственно вопрос, как можно подключить этот модуль неявно? т.е. при вызове какой либо функции из dop.bpl проверить его наличие и при положительном результате вызвать функцию, при отрицательном же просто сказать что "извините но такая то функция недоступна."
если можно то с каким нибудь примером фух, надеюсь я понятно описал проблему, а то у мну с объяснением постоянно плохо...
eldalex вне форума Ответить с цитированием
Старый 22.11.2010, 16:01   #2
Stilet
Белик Виталий :)
Старожил
 
Аватар для Stilet
 
Регистрация: 23.07.2007
Сообщений: 57,097
По умолчанию

Если оттуда вызываются только функции то просто динамически загружать как обычную ДЛЛ, если оттуда используются компоненты то если не ошибаюсь придется и их полностью переписать на динамическую загрузку.
Если что можно в dpr проверить через FileExists на наличие этого файла и вывести сообщение о ошибке. Но я бы не стал парится, раз программа сама позаботилась о выводе сообщения, пусть не такого как тебе хочется.
I'm learning to live...
Stilet вне форума Ответить с цитированием
Старый 23.11.2010, 08:33   #3
eldalex
Пользователь
 
Регистрация: 01.09.2010
Сообщений: 52
По умолчанию

к сожалению проблема не в сообщении, проблема в том, что после этой ошибки модуль main.bpl не подгружается вовсе, и все, что на нем висит, перестает работать а специфика такова что dop.bpl это дополнение и его вполне может и не быть. не перекомпилировать же всякий раз main.bpl в зависимости от того, входит ли в поставку dop.bpl или не входит...
eldalex вне форума Ответить с цитированием
Старый 23.11.2010, 08:42   #4
Stilet
Белик Виталий :)
Старожил
 
Аватар для Stilet
 
Регистрация: 23.07.2007
Сообщений: 57,097
По умолчанию

В этом случае тебе стоит почитать о том как делают плагины. Там описано решение твоей проблемы.
I'm learning to live...
Stilet вне форума Ответить с цитированием
Старый 23.11.2010, 10:42   #5
eldalex
Пользователь
 
Регистрация: 01.09.2010
Сообщений: 52
По умолчанию

Пытаюсь сделать так:
описал в dop.bpl функцию
Код:
unit dop_unit;

interface
uses
  Graphics;
Function Myfuction(ID:longint; PID:longint; DID:longint; PKID:longint):TPicture;

exports
 Myfuction index 1;
...//дальше сама функция и еще всякие мелочи
теперь пытаюсь вызвать ее из main.bpl

Код:
procedure TProtocol.InsertGrPrNew;
var
  wPict             : TPicture;
  wJp               : TJpegImage;
  hndBPLHandle  : THandle;
  pfun              : pointer;
begin
  try 
    hndBPLHandle := loadLibrary ( 'dop.bpl' );
    if hndBPLHandle <> 0 then
    begin
      // BPL найдена. получаем адрес функции
      pfun:= getProcAddress ( hndBPLHandle, 'Myfuction' );
      // если адрес функции найден
      if addr ( pfun ) <> nil then
      begin
        showMessage ('нашел функцию');
        wPict := TPicture.Create;
        wJp := TJpegImage.Create;                                           
        wPict :=pfun(FEditor.ID,FEditor.PID,strtoint(CurrentInfo.DID),FEditor.PKID); << ругается на эту строку, говорит что "missing operator or semicolon"
        if wPict.bitmap.empty = false then                                  
        try
          wJp.Assign(wPict.Bitmap);
          FEditor.InsertPicture('##Picture_GRNEW##', wJp, rvvaBaseline);  
        finally
          wPict.Free;
        end; 
      end
      else
        showMessage ( 'не нашел функцию' );
    end
    else
      // BPL не найдена ("handleable")
      showMessage ( 'не нашел bpl' );

  finally
    // liberar
    freeLibrary ( hndBPLHandle );
  end;
обычно ошибка такая возникает когда пропущена ; но тут не пропущено... как правильно вызвать функцию с параметрами?
если просто оставить сообщение о том что он нашел функцию, оно выскакиевает, т.е. вроде как работает. хотя опять же не факт(

-----------------

а, все разобрался)

Последний раз редактировалось eldalex; 23.11.2010 в 11:50.
eldalex вне форума Ответить с цитированием
Старый 26.11.2010, 15:12   #6
eldalex
Пользователь
 
Регистрация: 01.09.2010
Сообщений: 52
По умолчанию

Можно еще глупый вопрос?
что значит stdcall?
вот я описываю функцию
Код:
Function Myfuction(ID:longint; PID:longint; DID:longint; PKID:longint):TPicture; export;stdcall;
так указанно во всех примерах которые я видел.
но при вызове этой функции из 4х параметров правильно приходит только 1, остальные приходят совершенно другими числами. и плюс к этому вызов функции у меня почему то зациклился, она начинала вызываться n'ное количество раз. ну или если не ставить showmessage на выходе (пошагового решима нет, так что приходится отлаживать таким вот нехитрым способом.) то прога полностью вылетает.

если же описать вот так:
Код:
Function Myfuction(ID:longint; PID:longint; DID:longint; PKID:longint):TPicture; export;
то функция вызывается и отрабатывает правильно.
eldalex вне форума Ответить с цитированием
Старый 26.11.2010, 16:56   #7
Stilet
Белик Виталий :)
Старожил
 
Аватар для Stilet
 
Регистрация: 23.07.2007
Сообщений: 57,097
По умолчанию

Загляни сюда:
http://ru.wikipedia.org/wiki/%D0%A1%...dcall.2Fwinapi
I'm learning to live...
Stilet вне форума Ответить с цитированием
Старый 29.11.2010, 09:16   #8
eldalex
Пользователь
 
Регистрация: 01.09.2010
Сообщений: 52
По умолчанию

Прочитал... потом погуглил и еще почитал...
в статье написано:
Цитата:
Очистку стека производит вызываемая подпрограмма.
это происходит автоматически или надо прописывать ручками?

Последний раз редактировалось eldalex; 29.11.2010 в 09:48.
eldalex вне форума Ответить с цитированием
Старый 29.11.2010, 12:19   #9
Alexei91
Заблокирован
Форумчанин
 
Аватар для Alexei91
 
Регистрация: 30.12.2009
Сообщений: 544
По умолчанию

По-моему ручками,это же не Java с автоматическим "мусоросборником".
Темы для WordPress. Русские WordPress шаблоны
Alexei91 вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Как вызвать функцию из функции ? PheonixS JavaScript, Ajax 3 16.12.2010 05:35
Как вызвать функцию из юнита? Des Общие вопросы Delphi 5 06.11.2010 12:47
подскажите программу если таковая есть! rhcp Софт 0 14.09.2009 01:10
Как вызвать функцию? blackstersl Общие вопросы Delphi 10 07.06.2009 19:22
Вызвать адрес памяти как функцию XAOC-forever Общие вопросы Delphi 18 07.03.2009 20:32