I think I've sorted this but I'd appreciate being kicked if it looks like I'm doing something badly wrong.
What determines the constructor that's called when an object's created?
I've got a couple of classes defined like this:
TB5500BaseUnit=
class(TObject)
constructor Create(enum: integer; mnem: String7; unitIndex:integer; unitDesignate: integer; cc: TObject);
..
TB5500SPOUnit=
class (TB5500BaseUnit)
constructor Create(enum: integer; mnem: String7; unitIndex:integer; unitDesignate: integer; cc: TObject);
..
The actual objects being created are in response to configuration tables and files:
var
unitClass: class of TB5500BaseUnit; (* Ancestor of all I/O devices *)
u: TB5500BaseUnit;
name: string; (* For debugging *)..
unitClass := LookupUnitType( { from device name } );
name := unitClass.ClassName; (* For debugging *)
name := ''; (* Make sure it's wiped *)
u := unitClass.Create(Ord(mnem), specs.unitName,
specs.unitIndex, specs.designate, self);
name := u.ClassName; (* For debugging *)
thisUnit[specs.unitIndex] := u;If I was trying to create a TB5500SPOUnit I was finding that unitclass was set correctly, and that u was getting a valid type with (later) public methods declared as overrides being available. The odd thing was that TB5500SPOUnit.Create() was not being called, but instead TB5500BaseUnit.Create().
I find that if I explicitly decorate TB5500BaseUnit.Create() as virtual and TB5500SPOUnit.Create() as override then TB5500SPOUnit.Create() is called correctly. I didn't think this was necessary, but on reflection I assume that it's because u is declared as a TB5500BaseUnit: the variable's compile-time rather than run-time class is being used for the constructor unless explicitly overridden.
Is there an obvious way of tiying this up that I'm overlooking?
