Let’s say I have an “abstract” class called Base, and several others classes Class1, Class2, Etc. that inherit from the Base class. I want to be able to create instances of Class1, etc. from a shared method in the Base class. e.g. I have a shared method in Base:
function Instance() as Base
I would like to be able to call
dim c as Class1 = Class1.Instance
and return a Class1 instance, without having every class have its own Instance method.
I have not been able to figure out if this is doable or not. Introspection seems only to be able to construct information from either an object of a class, or from a call to GetTypeInfo with the name of the class as parameter.
Well, the reason for this “theoretical” discussion is so that all of Base’s subclasses can only have a single instance, which I would enforce via the Instance method (i.e. if an instance already exists, return it, otherwise create a new object).
Sure I could implement this separately for every subclass, but it gets tedious and prone to error.
That’s an interesting take. However it means creating an object that, if one of the class already exists, would need to get thrown away. Also there is no way to return the shared instance from the constructor. i.e. with
Yes, if each subclass implements it’s own shared system, but I want to do it from a base class shared system. Can’t think of any way to do it in Xojo. Easy enough in say, Swift.
Anyway I might have to bite the bullet and do it multiple times.
Correction, it looks like you can’t use “Shared()” as the method name, because that’s a reserved word in Xojo. (I chose ‘Shared’ because that’s how Swift does it).
Here’s a cleaned up version that actually compiles:
Class1:
Public Shared Function SharedInstance() As Class1
static c as new Class1 // Static variables are Application-global, so the "new" will only happen once
return c
End Function
Private Sub Constructor()
// by making the constructor Private, we prevent code from creating a new instance.
// e.g. this code
// dim C as new Class1
// will no longer compile outside of Class1
End Sub
If you wanted to do the bookkeeping in the Base class, I think that’s possible, but not necessarily any less code to write.
OK, so the particular Base class I’m looking at is a subclass of DesktopWindow, so the singleton code is a bit more complex since you need to reconstruct the DesktopWindow if it was subsequently closed, requiring nil-ing the instance property when the window closes, which means a separate private shared instance variable rather than a static variable (although I guess one could use a WeakRef, with even more code).
Anyway, it would seem that there’s no way to encapsulate all this stuff in the Base class, so I’m gonna bite the bullet and just reproduce the code for each subclass of the Base class.
in the window CancelClose event, simply hide the window rather than closing it - later on you simply Show it rather than re-creating it. (You need to handle the case there the app is quitting, in which case you do need to close the window properly)
Yes, but Implicit Instance is an abomination (IMHO). I don’t want these windows to hang around, hidden, and consuming resources. When I close them, I want them to go away.