Composant et affectation d'une propriété
Bonjour,
Dans un composant (visuel), j'ai une propriété property DataSet: TDataSet.
Lorsque j'associe par l'Inspecteur d'Objet par exemple un Zquery1 déposé sur la Form à la dite propriété, pas de problème.
Si je change le nom du zQuery1 par zQuery2 dans l'Inpecteur d'Objet du Zquery, le nouveau nom apparaît automatiquement dans la propriété DataSet de mon composant.
Mais si je sélectionne le zQuery1 de la Form et que je le supprime de cette dernière et si je veux ensuite sauvegarder ma Form à partir de l'IDE, j'obtiens un magnifique plantage... et la fermeture de Lazarus... et ceci même si le code est minimaliste dans le composant.
En clair, la modification du nom du composant zQuery est corrigée automatiquement dans la propriété DataSet de mon composant alors que visiblement la suppression du zQuery de la Form n'est pas gérée automatiquement par mon composant.
Pour l'instant, j'ai réglé le problème ainsi : je détecte la Form sur laquelle est posée mon composant, ce qui me permet de vérifier si la valeur 'zQuery1' contenue dans la propriété DataSet (de mon composant) correspond ou non à un zQuery existant dans la Form.
Cela m'oblige à utiliser une fonction spécifique pour le read au lieu d'un simple read FDataSet.
Je copie la partie utile du code.
Code:
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 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67
| type
TMyComponent = class(TCustomStringGrid)
private
{ Private declarations }
procedure SetDataSet(ADataSet: TDataSet);
function GetDataset: TDataSet;
procedure StringGridCreate(Sender: TObject);
function DataSetExist(xDataSet:TDataSet) : boolean;
protected
{ Protected declarations }
FormAOwner:TForm; {[En cas de suppression du DataSet dans l'IDE]}
public
{ Public declarations }
FDataSet: TDataSet;
constructor Create(AOwner: TComponent); override;
destructor Destroy; override;
published
{ Published declarations }
property DataSet: TDataSet read GetDataSet write SetDataSet;
end;
[...]
function TMyComponent.DataSetExist(xDataSet:TDataSet) : boolean;
{Objet : Vérifie si le DataSet existe notamment lors de sa suppression
directe dans l'IDE [sinon plantage de l'IDE]--> cf GetDataSet}
var
iLoc : Integer;
begin
Result := False;
if xDataSet = nil then exit;
if FormAOwner.ComponentCount <1 then exit;
for iLoc := 0 to FormAOwner.ComponentCount-1 do
if FormAOwner.Components[iLoc].Name = xDataSet.Name then begin
Result := True;
break;
end;
end;
constructor TMyComponent.Create(AOwner: TComponent);
begin
Inherited Create(AOwner);
{Détermination de la Form contenant le composant :
Nécessaire en cas de suppression du DataSet dans la Form
cf function DataSetExist() : boolean;}
FormAOwner := TForm(AOwner);
end;
function TMyComponent.GetDataset: TDataSet;
begin
if FDataSet = nil then
Result := nil
else begin
if not DataSetExist(FDataSet) then
Result := nil
else
Result := FDataset;
end;
end;
procedure TMyComponent.SetDataSet(ADataSet: TDataSet);
var i : integer;
begin
if ADataSet <> nil then begin
if not DataSetExist(ADataSet) then ADataSet := nil;
end;
if FDataSet <> ADataSet then FDataSet := ADataSet;
end; |
Cela a l'air de "fonctionner" au sens où le problème de suppression du DataSet dans la Form ne pose plus de problème. Mais cela me semble très lourd et inadapté : ce bricolage maison n'est certainement pas la bonne méthode. D'autant que si le DataSet est défini par programmation dans une autre Form (MyComponent1.DataSet := Form2.zQuery2) ou un DataModule, cela coince.
Quelle est la bonne approche ?
Merci de votre aide.
Cordialement. Gilles