Tengo una clase (MyClass
) que hereda la mayor parte de su funcionalidad de un objeto incorporado Qt (QGraphicsTextItem
). QGraphicsTextItem
hereda indirectamente de QObject
. MyClass
también implementa una interfaz, MyInterface
.Uso de señales Qt y ranuras con herencia múltiple
class MyClass : public QGraphicsTextItem, public MyInterface
tengo que ser capaz de utilizar connect
y disconnect
en MyInterface*
. Pero parece que connect
y disconnect
solo funcionan en instancias QObject*
. Como Qt no admite herencia múltiple de clases derivadas de QObject, no puedo derivar MyInterface
de QObject
. (Tampoco tendría mucho sentido para una interfaz de todos modos)
Hay discussion of the problem online, pero la solución propuesta es bastante inútil en el caso común (acceder a un objeto a través de su interfaz), porque no se puede conectar las señales y ranuras desde MyInterface*
pero deben convertirlo al tipo derivado. Dado que MyClass
es una de las muchas clases derivadas de MyInterface
, esto requeriría sentencias "si huele mal" si-esto-arrojar-a-otra-cosa-si-que-arrojó-a-esa y derrota el propósito de la interfaz.
¿Existe una buena solución a esta limitación?
ACTUALIZACIÓN: me di cuenta de que si dynamic_cast
un MyInterface*
-QObject*
(porque yo sé MyInterface
todas las clases -derivado también hereda el tiempo de QObject
, parece que funciona Esto es:.
MyInterface *my_interface_instance = GetInstance();
connect(dynamic_cast<QObject*>(my_interface_instance), SIGNAL(MyInterfaceSignal()), this, SLOT(TempSlot()));
Pero este realmente parece que estoy pidiendo un comportamiento indefinido ....
¿Cómo y cuándo declaras MyInterfaceSignal? –
'MyInterfaceSignal' se declara como un método virtual puro protegido * sin señal * en' MyInterface', y luego como * signal * en clases derivadas. Por lo tanto, el compilador asegura que las clases derivadas tienen el método, pero le corresponde al implementador marcarlo como una señal. Es cursi, porque no estoy * realmente * llamando a la tabla de llamadas virtuales desde 'MyInterface.MyInterfaceSignal', sino confiando en el hecho de que la macro SIGNAL es, al final del día, simplemente resolviendo un' char * 'nombre del método. –