Главная страница
Top.Mail.Ru    Яндекс.Метрика
Текущий архив: 2002.07.01;
Скачать: CL | DM;

Вниз

Передача значений из проекта в юнит   Найти похожие ветки 

 
alex-ran ©   (2002-06-20 12:19) [0]

Привет всем!!
Мне необходимо перед запуском главной формы приложения спросить у юзера имя и пароль и ес-но пустить или не пустить его в приложение. Я делаю так:

program Test;
uses
Forms, WinTypes, SysUtils, MainFfm in "MainFfm.pas" {MainForm};
type
TGetUserPass = function (AHandle: THandle; DBAlias, DBNameTable: ShortString): ShortString; StdCall;
EDLLLoadError = class(Exception);

{$R *.RES}

var
LibHandle : THandle;
GetUserPass : TGetUserPass;
ResDll : String;
begin
LibHandle := LoadLibrary("UserDll.Dll");
try
if LibHandle = 0 then
raise EDLLLoadError.Create("Не могу загрузить UserDll");
@GetUserPass := GetProcAddress(LibHandle, "GetUserPass");
if not (@GetUserPass = nil) then
ResDll := GetUserPass (Application.Handle, "RegulUser", "BankUser")
else
RaiseLastWin32Error;
finally
FreeLibrary(LibHandle);
end;
if ResDll="" then Exit;
Application.CreateForm(TMainForm, MainForm);
Application.Run;
end.
Здесь GetUserPass - функция, возвращающая имя пользователя.
Не могу понять, как передать ее значение в MainForm
Помогите, плиз, решить проблему или посоветуйте как правильно ее реализовать?

P.S. Делать все это по Create главной формы все-же не хотелось бы, она и так перегружена.


 
kull ©   (2002-06-20 12:30) [1]

Application.CreateForm(TMainForm, MainForm);
MainForm.UserName := ResDll;

,где UserName свойство, которое ты сам определяешь.


 
alex-ran ©   (2002-06-20 13:05) [2]

Спасибо за совет.
Но только возникла новая проблема :(
Мне это свойство необходимо для обработки в событии onCreate главной формы. А последовательность событий такова:

Application.CreateForm(TMainForm, MainForm); -
TMainForm.FormCreate(Sender: TObject); -
и только затем MainForm.UserName := ResDll;

так что немного не подходит, может есть еще способ?




> kull


> kull ©



 
kull ©   (2002-06-20 13:09) [3]

Ну можно в юните с формой завести глобальную переменную
var UserName: string;
А потом ее проверять на OnCreate.


 
Skier ©   (2002-06-20 13:14) [4]

> alex-ran
Может быть так ?

Application.Tag := Integer(PChar(ResDll))
Application.CreateForm(TMainForm, MainForm);


TMainForm.FormCreate(Sender: TObject);
var
AUserPass : String;
begin
...........
AUserPass := PChar(Application.Tag);
...........
Application.Tag := 0;
...........
end;


 
alex-ran ©   (2002-06-20 13:18) [5]

> kull ©
Не понял, ведь присвонение MainForm.UserName := ResDll;
происходит после отработки OnCreate главной формы.
Или я чего-то недопонимаю?


 
Толик ©   (2002-06-20 13:25) [6]

А в конструктор MainForm не пробовали значения передавать? Помогает... Написать в классе TMainForm свой конструктор, в который и передавать login user"а:

constructor TMainForm(Owner: TComponent, User: string);
begin
FUser := User;
// вот теперь в OnCreate будет виден user, т.к. OnCreate вызывается в конструкторе родителя
inherited Create(Owner);
end;

только MainForm придётся создавать не через Application.CreateForm, а MainForm := TMainForm.Create(Application, User);



 
kull ©   (2002-06-20 13:29) [7]

Файл с формой:

.....
type

TMainForm = .....
...

...
end;

var
UserName: string; //вот переменная с юзером

implementation
......


Файл проекта:

...
MainFrm.UserName := ResDll; //вот передача юзера
Application.CreateForm(TMainForm, MainForm);
...



 
alex-ran ©   (2002-06-20 13:35) [8]

> Skier ©
К сожалению нет, я просто не стал в форуме усложнять и рисовать реальную задачу, теперь вижу что зря.
Моя функция из ДЛЛ-ки возвращает не ShortString a:
TMyRes : Array [1..4] of ShortString;
Можно конечно слить все элементы массива одну строку и ее передать, но а как потом разделить?


 
Skier ©   (2002-06-20 13:37) [9]

> alex-ran
TStringList умеет строки делить.
Через св-ва Text и CommaText


 
alex-ran ©   (2002-06-20 13:52) [10]

> kull ©
Снова не понял. Разве можно присваивать свойству объекта значение до создания экземпляра объекта?

> Толик ©
Нельзя ли в примере поподробнее (как объявить и т.д.), я еще не силен в переопределении конструкторов


 
Skier ©   (2002-06-20 14:05) [11]

> alex-ran


В DLL склеиваешь MyRes в одну строку.
Проще всего так
var
ii : Integer;
AStrList : TStringList;
AStrToSend : String;
MyRes : TMyRes;
begin
....
AStrList := TStringList.Create;
try
for ii := 1 to 4 do AStrList.Add(MyRes[1]);
AStrToSend := AStrList.CommaText;
finally
AStrList.Free;
end; //try
//Отсылаешь AStrToSend
....
end;


В "принимающей" программе получаешь строку
иделаешь с ней :

var
AReceivedStr : String; //строка полученная из DLL
AStrList : TStringList;
MyRes : TMyRes;
ii : Integer;
begin
.....
AStrList := TStringList.Create;
try
AStrList.CommaText := AReceivedStr;
for ii := 0 to AStrList.Count - 1 do
MyRes[ii + 1] := AStrList[ii];
finally
AStrList.Free;
end; //try
.....
end;


 
kull ©   (2002-06-20 14:27) [12]


> Снова не понял. Разве можно присваивать свойству объекта
> значение до создания экземпляра объекта?


MainFrm.UserName здесь MainFrm - это не объект, а имя юнита, просто уточняю в каком файле находится переменная UserName.


 
Толик ©   (2002-06-20 14:31) [13]

TUser = ...; //TUser - некий свой тип (либо строка, либо структура, да хоть класс - не важно), если это просто строка, тогда этого можно этого и не писать, а везде вместо TUser подставлять string

TMainForm = class(TForm)
...
private
FUser: TUser;
public
constructor Create(Owner: TComponent; User: TUser);
reintroduce; overload;
end;

constructor Create(Owner: TComponent; User: TUser);
begin
FUser := User; //в OnCreate проблем не будет!
inherited Create(Owner);
end;

Теперь следует понять, что значит главная форма приложения. Это та форма, которая идёт первой в списке создаваемых форм через CreateForm. Но использовать CreateForm нельзя, т.к. CreateForm передаёт в конструктор только один параметр - SELF. А нам необходимо передать ещё и TUser. Поэтому поступаем так:

{dpr-файл}

begin
Application.Initialize();
MainForm := TMainForm.Create(Application, GetUser()); // здесь GetUser - некая ф-я, возвращающая переменную TUser (все вызовы dll находятся внутри неё)
//А вот теперь указываем приложению, что MainForm - главная форма
TForm((@Application.MainForm)^) := MainForm;
Application.Run();
end;

вот собственно и всё, только следует не забывать, что GetUser() выделяет память под TUser, но не освобождает её. Эту память надо освобождать в деструкторе TMainForm.


 
alex-ran ©   (2002-06-20 14:44) [14]

> kull ©
Спасибо, работает. И по-моему так проще всего. :)

Спасибо всем кто откликнулся.

И в продолжение, по совету Толика пробовал менять (для начала упростил)
Application.CreateForm(TMainForm, MainForm); на
MainForm := TMainForm.Create(Application). и затем
Application.Run;

Так вот, при этом после отработки формы из ДЛЛ главная (MainForm) не появляется, а приложение завершает работу, что нужно еще сделать?


 
alex-ran ©   (2002-06-20 14:50) [15]

>Толик ©
Преогромное спасибо, буду знать.


 
alex-ran ©   (2002-06-20 16:12) [16]

>Толик ©
Блин, опять проблема.
На inherited Create(Owner) в конструкторе вываливаюсь с сообщением:
Access violation at address ...... in module "TEST.EXE"
Read of address fffffffff
Из-за чего это?



Страницы: 1 вся ветка

Текущий архив: 2002.07.01;
Скачать: CL | DM;

Наверх




Память: 0.51 MB
Время: 0.01 c
1-1034
tovSuhov
2002-06-18 12:59
2002.07.01
TListView - разноцветные строки - как?


14-1206
artgamer
2002-05-31 21:56
2002.07.01
Помогите с экзаменами 11 класс!


14-1188
Марина
2002-05-31 14:58
2002.07.01
СУБД INGRES


14-1209
Slava
2002-05-31 16:50
2002.07.01
Новые версии


3-887
maxim2
2002-06-06 21:58
2002.07.01
Как закрыть MDIchild форму