views:

219

answers:

3

I'm trying to write a component that inherits from TClientDataset. On the create of the component in design time I want to instantiate a list of common fields that are used within my framework. The code below will execute without errors and the field will appear at run time but not design time. Can anyone help me? I'm sure its something trivial!

{ InheritedClientDataset }

constructor InheritedClientDataset.Create(AOwner: TComponent);
var
  Field : TField;
begin
  inherited;

  Field := TField.Create(self);
  Field.Name := 'ATestField';
  Field.FieldName := 'Test';
  Field.SetFieldType(ftInteger);
  //Field.DataType := ftInteger;
  Field.Size := 0;
  Field.FieldKind := fkData;

  self.Fields.Add(Field);
end;
+1  A: 

Totally untested, but you should probably be adding to FieldDefs instead:

with FieldDefs.AddFieldDef do
begin
  DataType := ftInteger;
  Name := 'Field1';
end;

with FieldDefs.AddFieldDef do
begin
  DataType := ftString;
  Size := 25;
  Name := 'Field2';
end;

You may also have to add a call to CreateDataSet after the FieldDefs are added:

// After above code...
inherited CreateDataSet;
Ken White
creates a field def fine but the actual TField doesn't get added which is what I need thank you for replying though
Barry
That's why I mentioned the possible need to call CreateDataSet(); it should actually create the TField.
Ken White
+4  A: 

Try creating your field using its fieldtype. For example, TIntegerField.

  MyField := TIntegerField.Create(Self);
  MyField.FieldName := 'MyFieldName';
  MyField.DataSet := Self;
  MyField.Name := Self.Name + '_' + MyField.FieldName;

That should work.

It will be available to controls but not the Fields Editor.

yozey
cheers man that was the problem! many thanks!!!
Barry
Oh ok great. See me edit though about how it may not be available to your editor.
yozey
fields editor recognizes it fine in delphi 2007 :) exactly how I wanted! cheers again.
Barry
Ok well there you go. Happy coding, :).
yozey
+1  A: 

I have a feeling that in cases like this, you might be going against the design intention of the VCL component designtime. Fields are typically defined by someone who places a table object onto a data module, then set the dataset properties to a particular SQL or other table and selects the fields from that table, rather than a component with a fixed set of fields, which might be something problematic for the current architecture to support, even though you have a fix, are you sure there aren't problems with that approach?

Have you thought about an alternative approach? (Write a component with a public property that allows it to be connected to a dataset or datasource and put all your framework logic in that component). Leave the dataset class alone.

Do you really NEED to do an "IS A" relationship in OOP terms, or would your code actually be cleaner if you considered "HAS A link to a dataset" instead?

Warren P
Hi, Yeah thats what im actually intending to do, i've written a support component that provides the ClientDataset with a list of fields, so when a button is clicked on the menu it will automatically create them. The code up there was just for a quick example as I could test if they appeared in design time, thanks for bringing it up though.
Barry