![]() |
TListBox zugriffs Problem
Hallo,
ich habe gerade ein kleines Problem mit einer TListBox Komponente: Ich lasse einige einträge aus der Datenbank auslesen und in der ListBox speichern über eine prozedur (vorher wird noch .clear durchgeführt) jetzt ist aber das problem: ich habe neben meiner form-klasse noch eine weitere eigene klasse. und wenn ich jetzt aus dieser anderen klassen die prozedure zum füllen der liste aufrufe ("LoadClerks", also FormKlasse.LoadClerks), passiert..... NICHTS die schleife liest zwar korrekt die zeilen aus der (mysql-) datenbank aus (man kann sich mit showmessage ja das entsprechende feld ausgeben lassen), aber sämtliche routinen der listbox zeigen keine wirkung (items.add, items.clear etc.). Es kommt zwar keine Fehlermeldung, aber es passiert auch nichts. ich habe schon probiert quasi eine Kopie dieser LoadClerks prozedur in meiner zweiten Klasse zu erstellen und die dann dadrin aufzurufen (sie entspricht der "originalen" prozedur aus der FormKlasse, hat halt nur jeweils anstelle von Listbox.items.... FormKlasse.ListBox.items etc.) im moment steh ich hier vor ner wand und komm nicht so wirklich weiter :wall: hoffe mal, dass mir einer helfen kann ;) gruß rudi achja: man sollte vieleicht noch sagen, dass die prozedur LoadClerks aus der FormKlasse heraus aufgerufen (z.b. über einen button auf der form) wunderbar funktioniert. Also daran kanns nicht so wirklich liegen dann. meine zweite Klasse ist ein ableger einer TGroupBox und daraus funzt zwar das aufrufen; es passiert halt nur nichts |
Re: TListBox zugriffs Problem
zeig mal etwas code
|
Re: TListBox zugriffs Problem
Wird die Prozedur auch azfgerufen? Bist du mal mit F7 Zeile für zeile durchgegangen? Hast du mal BreakPoints gesetzt und dir mal diverse Inhalte von vorkommenden Variablen angekuckt?
Du musst uns schon etwas helfen und das Problem selber etwas eingrenzen, wenn nicht sogar finden. Helfen es zu lösen können wir dir dann. Aber du musst erst mal ein Problem präsentieren. ;) |
Re: TListBox zugriffs Problem
das ist zunächst die form:
Delphi-Quellcode:
type
TSchedClerks = class(TForm) btn_ok: TButton; lst_clerks: TListBox; Button1: TButton; procedure btn_okClick(Sender: TObject); procedure FormActivate(Sender: TObject); procedure lst_clerksClick(Sender: TObject); procedure FormClose(Sender: TObject; var Action: TCloseAction); procedure Button1Click(Sender: TObject); private FClerkBox: TClerkBox; { Private declarations } public constructor Create(AOwner: TComponent; SchedConfig: TSchedConfig); overload; procedure BeforeDestruction; override; procedure LoadClerks; procedure ClearClerks; { Public declarations } end; und das hier ist die Klasse, die zur laufzeit erstellt wird, ein paar daten anzeigt und vor ihrer zerstörung die datenbank aktualisiert (falls was geändert wurde) und dann auch die listbox in der Form aktualisieren soll mit der SchedClerks.LoadClerks Methode
Delphi-Quellcode:
type
TClerkBox = class(TGroupBox) btn_svupd: TButton; lbl_clrkcap: TLabel; txt_clerkname: TEdit; private FDataSetID: integer; FChanged: boolean; procedure SetID(id: integer); procedure SetChanged(Sender: TObject); procedure UpdateEntry; procedure InsertEntry; procedure ButtonAction(Sender: TObject); public property DataSetID: integer read FDataSetID write SetID; constructor Create(AOwner: TComponent); override; procedure BeforeDestruction; override; end; und das hier ist die LoadClerks prozedur:
Delphi-Quellcode:
das mit dem TStaffObj habe ich eben der einfachheit nicht erwähnt. Weil ich zu jedem Namen auch noch die DatensatzID festhalten will, speicher ich das halt in einem kleinem Objekt in der ListBox
procedure TSchedClerks.LoadClerks;
var Result: TResultID; Row: TMyRow; i: integer; Clrk: TStaffObj; begin ClearClerks; Result := FMySQL.Query('SELECT * FROM staff ORDER BY name'); if FMySQL.LastErrorNo = 0 then begin SetLength(Row,0); for i := 0 to FMySQL.AffectedRows(Result)-1 do begin Row := FMySQL.FetchRow(Result); Clrk := TStaffObj.Create; clrk.Name := row[1]; clrk.ID := strtoint(row[0]); lst_clerks.Items.AddObject(row[1],clrk); end; end; FMySQL.FreeResult(Result); end; aber selbst wenn ich das sein lasse und nur lst_clerks.Items.Add(row[1]) mache, passiert ja nichts also kann das keine fehlerursache sein die prozedur ClearClerks macht nichts, ausser in einer schleife einmal durch die einträge der Listbox zu laufen und die gespeicherten Objekte zu zerstören, bevor ein lst_clerks.Items.Cler aufgerufen wird. (funktionert aber aus demselben grund, warum auch die LoadClerks nicht funktioniert anscheinend nicht) |
Re: TListBox zugriffs Problem
@Luckie
ja wie bereits erwähnt lasse ich z.B. die ergebnisse der datenbank ausgeben in einer showmessage in der LoadClerks prozedur Die Daten werden korrekt ausgelesen, nur sämtliche operationen an der Listbox wie löschen, hinzufügen, ändern etc. zeigen keine wirkung, wenn das aus dem TClerkBox objekt heraus durchgeführt wird |
Re: TListBox zugriffs Problem
bevor ich jetzt erstmal weg muss, sollte man ggf. noch erwähnen, dass diese Form aus einer anderen Form heraus mit ShowModal erzeugt wird; falls das wichtig ist:
Delphi-Quellcode:
(das nur am rande)
ClerkWindow := TSchedClerks.Create(nil,SchedConfig);
with ClerkWindow do begin top := (screen.Height div 2) - (height div 2); left := screen.Width div 2 - width div 2; ShowModal; end; ClerkWindow.Free; |
Re: TListBox zugriffs Problem
wo und wie (und wann) rufst du LoadClerks auf ?
hast du irgendwo BeginUpdate / EndUpdate bei den Items der ListBox ? (Code von ClearClerks ?) eventuell eine zweite kopie der Form / ListBox ? |
Re: TListBox zugriffs Problem
meinst du mit BeginUpdate/EndUpdate, dass ich quasi das TStrings Objekt (also .Items) der listbox ändere, das ganze aber aus irgendwelchen gründen nicht dargestellst wird? (also quasi geupdated?)
und hier der ClearClerks Code:
Delphi-Quellcode:
wie gesagt, erfüllt seinen zweck, wenn aus der FormKlasse selbst aufgerufen
procedure TSchedClerks.ClearClerks;
var i: integer; begin if assigned(FClerkBox) then begin FClerkBox.Free; FClerkBox := nil; end; for i := 0 to lst_clerks.Count - 1 do begin TStaffObj(lst_clerks.Items.Objects[i]).Free; end; lst_clerks.Items.Clear; end; aber nicht, wenn es aus aus der TClerkBox-Klasse heraus aufgerufen wird /edit: der teil mit FClerkBox.Free dient nur dazu, eine ggf. angezeigte GroupBox zu schließen. Wobei mir jetzt gerade erst auffällt, dass sich die Klasse ja quasi aus sich selbst heraus abschießen würde. Eine prozedur der Instanz von TClerkBox ruft die methode ClearClerks der Instanz von TSchedClerks (also der form) auf, welche wiederrum eigentlich genau die Instanz der TClerkBox zerstören sollte, die ClearClerks aufgerufen hat. gibt aber keinen fehler also entweder bin ich zu 100% ein opfer von "betriebsblindheit" geworden oder ich versteh grad gar nichts mehr *g* |
Re: TListBox zugriffs Problem
zeig mal, wo du LoadClerks aufrufst,
übrigens, statt
Delphi-Quellcode:
kannst
if assigned(FClerkBox) then
begin FClerkBox.Free; FClerkBox := nil; end;
Delphi-Quellcode:
verwenden
if assigned(FClerkBox) then FreeAndNil(FClerkBox);
|
Re: TListBox zugriffs Problem
Delphi-Quellcode:
zur erklärung der BeforeDestruction methode:
procedure TClerkBox.BeforeDestruction;
begin if FChanged then begin if FDataSetID <> -1 then UpdateEntry else InsertEntry; end; inherited BeforeDestruction; end; procedure TClerkBox.UpdateEntry; begin if FChanged then begin FMySQL.Query('UPDATE staff SET name='''+txt_clerkname.Text+''' WHERE id='+inttostr(FDataSetID)); if FMysql.LastErrorNo <> 0 then showmessage(FMySQL.LastErrorMsg); FMySQL.FreeResult(FMySQL.LastResultID); FChanged := false; Caption := 'Information:'; LoadClerks; end; end; procedure TClerkBox.InsertEntry; begin if FChanged then begin FMySQL.Query('INSERT INTO staff (name) VALUES('''+txt_clerkname.text+''')'); if FMysql.LastErrorNo <> 0 then showmessage(FMySQL.LastErrorMsg); FMySQL.FreeResult(FMySQL.LastResultID); FChanged := false; Caption := 'Information:'; LoadClerks; end; end; FChanged wird dann auf true gesetzt, wenn jemand den inhalt des textfeldes geändert hat (um nicht unnötig jedesmal einen eintrag zu updaten, der sich gar nicht geändert hat). FDataSetID speichert den primärschlüssel, um auch den richtigen datensatz in der db zu erwischen ist FDataSetID = -1, wird angenommen, dass das ganze als neuer Datensatz gespeichert werden soll |
Alle Zeitangaben in WEZ +1. Es ist jetzt 21:52 Uhr. |
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz