Форум: "Основная";
Текущий архив: 2002.10.31;
Скачать: [xml.tar.bz2];
ВнизОтличия обычного проекта и Dll-проекта Найти похожие ветки
← →
Starkom (2002-10-18 12:53) [0]Была прога с кучей кода. Оформили ее, как Dll, чтобы включить в другой Билдерный проект. Перестало работать очень многое (код не менялся). Капшены у форм присваиваться неправильно стали, кейпрессы в комбобоксах перестали обрабатываться. Да вообще много что перестало или стало по-другому работать!!!
Помогите, что делать в данной ситуации?
← →
Starkom (2002-10-18 15:50) [1]ну помогите, пожайлуста! Хотя бы возможные причины. А то мы не знаем даже, с какой стороны подойти.
← →
Opuhshii (2002-10-18 15:55) [2]"что делать в данной ситуации?"
посмотреть,.. пересобрать проект,... посмотреть,.. и дебажить, дебажить дебажить,...
← →
Starkom (2002-10-21 08:58) [3]да блин
что дебажить то?
← →
Bis (2002-10-21 09:08) [4]Ты бы описал хоть, какую среду используешь!
Я то знаешь ли есть особенности что и как прилинковывать...
← →
Starkom (2002-10-21 09:18) [5]Проект был отписан на Delphi 5
Затем переделан под Dll в нем же.
Проект, юзаюзий Dll, пишется на Builder 5.
← →
Bis (2002-10-21 09:39) [6]а как вызываешь формы дельфовские из буилдера?
и кстати, ты инстанцию передаешь?
← →
Петров Денис (2002-10-21 09:44) [7]В параметрах функций DLL есть пасквилевские строки (в смысле string)? Если есть - то неплохо переделать их в PChar.
Опять же, C++ и Delphi обычно используют разную организацию стека при вызове функций - эта проблема решается унификацией описания прототипов функций с каким-нибудь модификатором типа "stdcall".
← →
Starkom (2002-10-21 10:03) [8]просто вместо .dpr-ного
Application.Initialize;
Application.CreateForm(TMainForm, MainForm);
Application.Run;
вставили вызов функции из Dll -
procedure RunGen();
begin
MainForm:=TMainForm.Create(nil);
MainForm.Show();
end;
exports
RunGen;
Код MainForm вообще не меняли.
А насчет стека при вызове функций - в Билдере везде юзаем __fastcall
← →
NUU (2002-10-21 13:12) [9]Сорбственно а чего Вы хотели чтобы было.
Естественно глючит, Application.Run надо было бы и оставить.
Да и MainForm инициализироваться должна Application.CreateForm(TMainForm, MainForm);Иначе она Application.MainForm никогда и не будет.Посмотри сырцы Application.CreateForm и все поемешь.
← →
Севостьянов Игорь (2002-10-21 13:21) [10]Тебя же спросили. А где объявление в Delphi варианте ?
interface
....
procedure RunGen; stdcall;
....
implementation
....
procedure RunGen; stdcall;
begin
....
end;
← →
Bis (2002-10-21 13:22) [11]а зачем вообще чего-то придумывать надо было?
Буилдер напрямую поддерживает все юниты из Дельфи!
← →
Starkom (2002-10-21 14:15) [12]2 Севостьянов Игорь: А в Дельфях же все функции по умолчанию stdcall. Зачем его явно указывать?
2 NUU: А она и не должна быть Application.MainForm
По идее, тут вообще другой Application, основного проекта.
Или у длл должен быть свой объект класса TApplication?
← →
Bis (2002-10-21 14:31) [13]У длл свой TApplication,
но советую Handle передать из буилдера и присвоить в длл.
И формы надо создавать тоже самому, лучше по мере необходимости, через Application или нет, неважно.
И кто тебе сказал, что по умолчанию stdcall ?
В общем попробуй сначала написать простую dll без всяких форм и вызов хотя бы одной функции чтоб был успешным, можно показать ShowMessage в нем
← →
Starkom (2002-10-21 14:39) [14]2 Bis:
"но советую Handle передать из буилдера и присвоить в длл."
хэндл экземпляра TApplication?
А насчет простой длл - длл то у меня работает, но некоторые вещи почему-то работают неправильно.
Насчет stdcall, конечно же, проглючил. Если в Билдере везде указывать __fastcall, то в Дельфях же можно ничего не писать. Или не так?
← →
NUU (2002-10-21 14:53) [15]у длл все свое, как у отдельного приложения.
Приведи код своей простой длл и скажи чего конкретно работает неправильно?
А то непонятно.
← →
NUU (2002-10-21 14:56) [16]Если после заголовка метода отсутствует соглашение о вызове, то по умолчанию Delphi использует соглашение register.
← →
Starkom (2002-10-21 14:58) [17]register в Дельфях и __fastcall в Билдере - это же одно и то же.
← →
Starkom (2002-10-21 15:01) [18]то есть, по идее такой код правильнее?
Application.Initialize();
Application.CreateForm(TMainForm, MainForm);
MainForm.Show();
← →
NUU (2002-10-21 15:01) [19]Это понятно код ты дашь или нет?
← →
Bis (2002-10-21 15:03) [20]2Starkom
Да, тот самый хендл
в dll вызов функций по stdcall, почитай внимательно!
тебе трудно написать это слово? Даже если как ты считаешь в Булдере так и есть?
← →
Starkom (2002-10-21 15:08) [21]2 NUU: какой конкретно?
Там 5 мегов в архиве одних .pas файлов
← →
NUU (2002-10-21 15:18) [22]
> А насчет простой длл - длл то у меня работает, но некоторые
> вещи почему-то работают неправильно.
дпрник длл.
Ты функции из длл статически юзаешь или динамически?
← →
Starkom (2002-10-21 15:25) [23]
library ProjectDll;
uses
ShareMem,
Windows,
SysUtils,
Classes,
Forms,
MainUnit1 in "..\MainUnit1.pas" {MainForm},
{$R *.RES}
procedure RunGen();stdcall;
begin
MainForm:=TMainForm.Create(nil);
MainForm.Show();
end;
exports
RunGen;
begin
end.
и все.
вызов RunGen -
void __fastcall TFormManager::N3Click(TObject *Sender)
{
HINSTANCE Dll = GetModuleHandle("ProjectDLL.dll");
if(Dll == NULL)
{
Dll = LoadLibrary("ProjectDLL.dll");
}
void __fastcall (__import *Generator)(void);
if (Dll)
{
Generator = (void __fastcall (__import *)(void)) GetProcAddress(Dll,"RunGen");
if (Generator)
Generator();
else
ShowMessage("?????? RunGen ?? ???????");
// FreeLibrary(Dll);
}
else
ShowMessage("ProjectDLL.dll ?? ???????");
}
//---------------------------------------------------------------------------
← →
Bis (2002-10-21 15:35) [24]Вот если б ты использовал форму в модальном режиме, все было бы нормально.
А здесь могут быть свои камни.
Где-то мелькал тут компонент, позволяющий использовать такие формы в dll, не помню только ...
А кто у тебя потом формы освобождает?
← →
Starkom (2002-10-21 15:40) [25]2 Bis: пока никто :)) Планировали, что RunGen будет возвращать указатель на MainForm - а там уже все будет убиваться, очищаться.
Теперь, вообще, непонятно, как делать.
ShowModal использовать нельзя (задача такая).
← →
Bis (2002-10-21 15:52) [26]Может это тебе поможет:
http://www.torry.net/vcl/vcltools/plugins/libmgr.zip
Менеджер библиотек DLL. Позволяет загружать и показывать формы, определенные в DLL, безмодальным (синхронным) способом. Поэтому не придется вызывать ShowModal для показа формы, если необходимо выгрузить библиотеку.
← →
NUU (2002-10-21 16:05) [27]Попробуй так:
library ProjectDll;
uses
ShareMem,
Windows,
SysUtils,
Classes,
Forms,
MainUnit1 in "..\MainUnit1.pas" {MainForm},
Var
pApp,pScr:pointer;
// Init and Free Functions *****************************************************
procedure InitLib(App,Scr:pointer);stdCall;
begin
pApp :=Application;
pScr :=Screen;
Application :=App;
Screen :=Scr;
end;
procedure DoneLib;stdCall;// собственно необязательно, но желательно
begin
Application :=pApp;
Screen :=pScr;
end;
procedure RunGen();stdcall;
begin
MainForm:=TMainForm.Create(nil);
MainForm.Show();
end;
exports
InitLib,
DoneLib,
RunGen;
begin
end.
После окрытия бибилиотеки Dll = LoadLibrary("ProjectDLL.dll");
вызови InitLib из нее и передай Application и Screen из основной программы;
У меня так работает :)
← →
Bis (2002-10-21 16:18) [28]2NUU
Позвольте узнать, где это у вас работает?
Выхов из Дельфи будет работать, а вот из Буилдера сомневаюсь
Реализация объектов в Дельфи и С++ разная изначально
← →
NUU (2002-10-21 16:37) [29]ну у меня собственно из делфи и работает. Дык главное подход :)))
Страницы: 1 вся ветка
Форум: "Основная";
Текущий архив: 2002.10.31;
Скачать: [xml.tar.bz2];
Память: 0.51 MB
Время: 0.01 c