J'utilise Delphi 7 avec un certain nombre de composants tiers. Mon application stub principale charge un certain nombre de DLL, qui sont divers modules comme les créanciers, les débiteurs, les commandes d'achat, et ainsi de suite.FindComponent ne trouve pas les composants créés au moment de l'exécution
J'ai un problème avec FindComponent()
. 99% du temps, cela fonctionne comme il se doit. Mais pas pour le code ci-dessous. J'essayais de créer un rapport de formulaire, où je garde tous les détails des critères de sélection de rapports dans un tableau, puis je crée les critères à la volée. En théorie, cela devrait fonctionner parfaitement, mais pour une raison quelconque après la création des composants, FindComponent()
ne peut pas les trouver.
try
for i := gbSelectionCriteria.ComponentCount - 1 downto 0 do begin
ShowMessage(gbSelectionCriteria.Components[i].Name);
gbSelectionCriteria.Components[i].Free;
end;
// The above loop to remove the components from the groupbox works fine
// Creating the components works
fSysData.tbSelectionCriteria.First;
while not fSysData.tbSelectionCriteria.EOF do begin
case fSysData.tbSelectionCriteriaComponentType.AsInteger of
1 : begin // TMyAdvEdit
with TMyAdvEdit.Create(gbSelectionCriteria) do begin
Visible := False;
Parent := gbSelectionCriteria;
Name := fSysData.tbSelectionCriteriaName.AsString;
Left := fSysData.tbSelectionCriteriaLeft.AsInteger;
Top := fSysData.tbSelectionCriteriaTop.AsInteger;
Width := fSysData.tbSelectionCriteriaWidth.AsInteger;
LabelCaption := fSysData.tbSelectionCriteriaCaption.AsString;
LabelPosition := AdvEdit.lpLeftCenter;
LabelAlwaysEnabled := True;
LabelTransparent := True;
EditType := MyEditType[fSysData.tbSelectionCriteriaDataType.AsInteger];
Text := '';
OnClick := GetClickEvent(fSysData.tbSelectionCriteriaOnClickEvent.AsString);
OnDblClick := GetClickEvent(fSysData.tbSelectionCriteriaOnDblClickEvent.AsString);
OnKeyPress := GetKeyPressEvent(fSysData.tbSelectionCriteriaOnKeyPressEvent.AsString);
Visible := True;
// at this point findComponent finds nothing
if FindComponent(Name) <> nil then
ShowMessage(Name+' Created');
end;
edEdit.OnClick := GetClickEvent(fSysData.tbSelectionCriteriaOnClickEvent.AsString);
edEdit.OnDblClick := GetClickEvent(fSysData.tbSelectionCriteriaOnDblClickEvent.AsString);
edEdit.OnKeyPress := GetKeyPressEvent(fSysData.tbSelectionCriteriaOnKeyPressEvent.AsString);
edEdit.Visible := True;
if FindComponent(edEdit.Name) <> nil then
ShowMessage(edEdit.Name+' Created');
end;
2 : begin
end;
3 : begin
end;
4 : begin
end;
5 : begin
end;
6 : begin
end;
7 : begin
end;
8 : begin
end;
end;
fSysData.tbSelectionCriteria.Next;
end;
if fSysData.tbSysReports.Locate('ReportID', TAdvOfficeRadioButton(Sender).Tag, []) then begin
ReportData.ReportID := TAdvOfficeRadioButton(Sender).Tag;
ReportData.RepName := fSysData.tbSysReportsReportName.AsString;
ReportData.RepTitle := fSysData.tbSysReportsReportTitle.AsString;
ReportData.RepModule := fSysData.tbSysReportsModule.AsString;
ReportData.RepOrientation := fSysData.tbSysReportsReportOrientaton.AsString;
ReportData.RepPageIndex := fSysData.tbSysReportsCriteriaPageIndex.AsInteger;
end;
finally
end;
Le processus des rapports est:
utilisateur clique sur un bouton
Les boutons radio sont créés à partir du bouton cliquez sur
utilisateur clique sur un bouton radio
Signaler les critères est créé à partir du bouton radio, cliquez sur
L'utilisateur entre des données ou DblClicks pour sélectionner des données dans une liste.
utilisateur clique bouton Aperçu pour consulter le rapport - c'est là FindComponent échoue et retourne nul ..
Tout le code a fonctionné avant quand j'avais créé tous les critères au moment de la conception, puis ajouté le code au dessus.
Le code ci-dessous fait partie de ce qui doit être ajouté à la requête pour récupérer les données du rapport:
if Length(TMyAdvEdit(FindComponent('edQuoteReference')).Text) > 0 then
qryTempTable.SQL.Add(' and q.UserReference = "' + TMyAdvEdit(FindComponent('edQuoteReference')).Text + '"');
Ceci est la première fois FindComponent()
échoue et va pas plus loin.
J'ai essayé différentes façons de créer les composants, mais chacun d'entre eux entraîne une violation d'accès car le composant est nul.
J'ai regardé partout, et j'ai essayé tout ce que je peux penser, pour une solution à ce problème.
J'ai quelques conseils. Vous avez collé une grande quantité de code étranger ici et il est difficile de voir le bois pour les arbres. Ce serait tellement plus facile pour tout le monde, surtout vous, si vous aviez réduit le code à une forme minimale. A [mcve]. –
(1) Pour votre propre bénéfice, arrêtez d'utiliser ** avec **. Avez-vous une idée du nombre de fois où vous avez accidentellement référencé un membre de votre "TMyAdvEdit" nouvellement créé sans le savoir? Il n'y a *** *** *** aucune raison impérieuse d'utiliser ** avec **; au minimum, vous pouvez toujours déclarer une variable locale telle que 'NewAdvEdit' (2) Je ne voudrais pas non plus déranger' NewAdv.Visible: = False; 'et plus tard en le définissant à' True'. À moins que votre composant ne fasse quelque chose d'obscur, vous ne devriez pas traiter un message de peinture entre ces 2 lignes. –