Entwickler-Ecke

Sonstiges (Delphi) - Verwirrung beim RECORD


mats - Di 21.08.18 13:36
Titel: Verwirrung beim RECORD
Hallo,

Alles ganz einfach, und wieder nicht. Unit1 mit einem Record (Adressdaten, alles Strings) und Label zur Eingabe, Button usw. Wenn ich den Button drücke, wird vom Label gelesen und in den Record geschrieben, dann wird Unit2 aufgerufen um den Inhalt vom Record auszugeben. Funktioniert aber nur, wenn ich auf Unit2 auch einen Button drücke und einem Label den Inhalt von User.Name zuweise. Wenn ich den Record im OnCreate-Ereignis auslesen will und dem Label zuweisen, dann klappts nicht - Warum?
Vielleicht kann mir jemand die Frage beantworten? Ist im OnCreate in Unit2 der Record noch nicht 'geladen'? Ich hab keine Idee..

auf Ideen wartend...

Mats


jaenicke - Di 21.08.18 13:41

Ohne Quelltext lässt sich dazu wenig sagen.

Eine Möglichkeit wäre, dass du die Datei nicht schließt bevor das zweite Formular aufgerufen wird. Dann gibt es vielleicht ein Problem beim Zugriff durch das zweite Formular.

Es gibt davon unabhängig aber auch deutlich bessere Möglichkeiten als die alten typisierten Dateien, in denen Records gespeichert werden. Hast du die Vorgabe Records zu verwenden?

// EDIT:
Missverständnis...


mats - Di 21.08.18 15:48

Hallo,

die 'Vorgabe' Records? Leider weiß ich nicht was das ist. Das Fenster 1 (dort werden die Daten erzeugt) habe ich geschlossen mit Form1.Close;
Hier zwei Bilder, die die Sache verdeutlichen (was ich meine), bzw. nicht.

Record1.png -> funtioniert NICHT. Label leer.

Record2.png -> bei klick funtioniert. Die Daten werden aus dem Record von Unit1 geladen. Aber warum klappts hier?


Mats


Delete - Di 21.08.18 16:34

- Nachträglich durch die Entwickler-Ecke gelöscht -


mats - Di 21.08.18 16:41

Hallo,

Sorry Frühlingsrolle, aber der/das (?) Record bekommt seine Daten in Unit1! Sorry auch an mich, hätte ich dazuschreiben sollen, die Bilder sind Unit2. Bei OnCreate (Unit2) werden keine Werte vom Record an die Label übergeben. 1 Sekunde später werden die Daten bei ButtonClick korrekt geladen. Als Notlösung geht folgendes: Unit2 -> OnAktivate -> ButtonClick. Ich habe das auch mit OnCreate versucht, da kommt nur die Hälfte der Daten an. Ein Zeitproblem / ein Ladeproblem???

Mats


Delete - Di 21.08.18 16:56

- Nachträglich durch die Entwickler-Ecke gelöscht -


jaenicke - Di 21.08.18 16:57

Wo ist denn User deklariert? Sinnvoller wäre auch Quelltext nicht als Bild zu posten, sondern als Text:

Unit1.pas
1:
2:
3:
4:
var
  a: Integer;
begin
  ...


Hier mal ein Beispiel wie das gemacht werden kann ohne die Events zu benutzen. Stattdessen schreibst du die Werte direkt in die Anzeige, wenn diese sich ändern.

MainFormUnit.pas
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
uses
  UserInfo, SecondFormUnit;

procedure TfrmMain.btnShowClick(Sender: TObject);
begin
  frmSecond.Free;
  frmSecond := TfrmSecond.Create(nil);
  frmSecond.UserInfo := TUserInfo.Create(edtFirstName.Text, edtFamilyName.Text);
  frmSecond.Show;
end;



SecondFormUnit.pas
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
20:
21:
22:
23:
24:
25:
26:
27:
28:
29:
30:
31:
32:
33:
type
  TfrmSecond = class(TForm)
    lblFirstNameDisplay: TLabel;
    lblFamilyNameDisplay: TLabel;
    btnClose: TButton;
    procedure btnCloseClick(Sender: TObject);
  private
    FUserInfo: TUserInfo;
    procedure SetUserInfo(const Value: TUserInfo);
  public
    property UserInfo: TUserInfo read FUserInfo write SetUserInfo;
  end;

var
  frmSecond: TfrmSecond;

implementation

{$R *.dfm}

procedure TfrmSecond.btnCloseClick(Sender: TObject);
begin
  Close;
end;

{ TfrmSecond }

procedure TfrmSecond.SetUserInfo(const Value: TUserInfo);
begin
  FUserInfo := Value;
  lblFirstNameDisplay.Caption := Value.FirstName;
  lblFamilyNameDisplay.Caption := Value.FamilyName;
end;


UserInfo.pas
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
type
  TUserInfo = record
    FirstName: string;
    FamilyName: string;
    constructor Create(const AFirstName, AFamilyName: string);
  end;

implementation

{ TUserInfo }

constructor TUserInfo.Create(const AFirstName, AFamilyName: string);
begin
  FirstName := AFirstName;
  FamilyName := AFamilyName;
end;

Das Projekt liegt auch komplett im Anhang.


mats - Di 21.08.18 17:13

Hallo,

vielleicht hab' ich es ein wenig umständlich erklärt. Der Record wird in Unit1 deklariert und bekommt auch dort seine Daten. Bei ButtonCklick -> Weiter schließt sich Unit1 und öffnet sich Unit2 und die Daten sollen angezeigt werden. (Die Daten sind nicht weg, wenn ich Unit1 schließe, wenn ich mit einen Button zurück gehe [also Unit1 öffne und die 2 schließe], sind die Daten noch in den EditFeldern und können noch geändert werden).
An die Möglichkeit für den Record eine eigene Unit zu schreiben hab ich auch schon dran gedacht, bin aber bei dem jetzigen Problem hängengeblieben. Ich werden den SourceCode erst mal ausprobieren.

Danke

Mats


mats - Di 21.08.18 18:42

Hallo,

Habe mir den Code angesehen und viele Anregungen gefunden. Wenn ich aber in meinem Record ca. 20 Variablen habe, gibt es da, beim deklarieren/überschreiben des Contructors eine andere Möglichkeit der Variablenübergabe?

Mats


Sinspin - Sa 25.08.18 15:58

Klar. Es ist ja nur in dem Beispiel im Constructor um weitere Methoden zu sparen.
zum beispiel so:

Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
//private der klasse
FValues: array [0..19of string;
//public der klasse
procedure SetValue(AIndex: integer; AValue: string);
function GetValue(AIndex: integer): string;
// --> füllen kannst du die Methoden selber, du postest ja auch lieber bilder anstatt einfach quelltext einzufügen ;-) 

//das ginge dann jetzt sogar mit eim property für den zugriff
property Values[AIndex: integer]: string read GetValue write SetValue;


jaenicke - Sa 25.08.18 16:13

Sinnvoller wäre dann eher eine Klasse, wenn es mit dem Array nicht geht (was ich vermute). Denn die kann man problemlos so nutzen:

Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
var
  UserInfo: TUserInfo;
begin
  ...
  UserInfo := frmSecond.UserInfo;
  UserInfo.FirstName := 'blub';
  UserInfo.FamilyName := 'boo';
...