Russian Qt Forum

Qt => Общие вопросы => Тема начата: mks от Январь 04, 2013, 15:54



Название: Система динамических расширений (Qt plugins)
Отправлено: mks от Январь 04, 2013, 15:54
Добрый день.
Читая книгу "Qt 4.7+ Практическое программирование на С++" автор Боровский, в главе касающейся динамических расширений, наткнулся на такую фразу:
"Определения сигналов и слотов не должны быть частью интерфейса. Интерфейс - это набор обычных виртуальных методов С++ и ничего более". Но объяснений почему так, в этой книге нет. С другой стороны просматривая исходники проекта rexloader (https://code.google.com/p/rexloader/source/browse/trunk/plugins/LoaderInterface.h) вижу что там в интерфейсах используются сигналы. Проект собирается и нормально работает. Объясните в чём тут загвоздка, и почему Боровский не рекомендует использовать сигналы в интерфейсе ?
Благодарю за внимание.


Название: Re: Система динамических расширений (Qt plugins)
Отправлено: Vass от Январь 04, 2013, 17:28
По определению интерфейс подразумевает лишь объявление некоторой сущности, не содержащие какой либо логики.
В С++ нет как такового понятия интерфейс, как например в Java.
Поэтому интерфейсом назывется класс, в котором все методы объявлены чисто виртуальными
Отсюда следует что, чтобы интерфейс оставался интерфейсом, а не становился просто абстрактным классом, он может наследоваться только от другого
интерфейса.
Но! Для того чтобы объявить и использовать сигналы и слоты, класс должен быть наследником QObject, а QObject - это вполне себе класс, причем даже не абстрактный.
Соответственно если вы наследуете "интерфейс" от QObject, то это уже и не интерфейс вовсе, а абстрактный класс.

Конечно, вы можете использовать этот абстрактный класс в своем коде как родительский класс далее (как вы и увидели в проекте-примере), но формально это уже не интерфейс.


Название: Re: Система динамических расширений (Qt plugins)
Отправлено: mks от Январь 04, 2013, 19:25
Спасибо, примерно так и предполагал.


Название: Re: Система динамических расширений (Qt plugins)
Отправлено: Dancing_on_water от Январь 04, 2013, 19:46
Может я все-таки не прав (давно было)

Но можно сделать такую штуку

Цитировать
class A
{
  Q_OBJECT
//виртуальные методы
 Q_SIGNALS:
 void testSignal();
}

class B: public QObject, public A
{
  Q_OBJECT
}
И далее юзать сигнал и это будет работать.


Название: Re: Система динамических расширений (Qt plugins)
Отправлено: Old от Январь 04, 2013, 20:03
И далее юзать сигнал и это будет работать.
moc пропустит класс A, т.к. он не является наследником QObject.


Название: Re: Система динамических расширений (Qt plugins)
Отправлено: Dancing_on_water от Январь 04, 2013, 20:32
мок не компилятор, для moc-а сигналом является макрос Q_OBJECT.


Название: Re: Система динамических расширений (Qt plugins)
Отправлено: Old от Январь 05, 2013, 10:37
мок не компилятор, для moc-а сигналом является макрос Q_OBJECT.
Теоретик? А ты попробуй. :)
И получишь от moc:
Error: Class contains Q_OBJECT macro but does not inherit from QObject


Название: Re: Система динамических расширений (Qt plugins)
Отправлено: Bepec от Январь 05, 2013, 10:41
Old прав, если класс не унаследован от QObject, никоим образом ты туда сигналы не впихнёшь.

Разве что переписать moc :D


Название: Re: Система динамических расширений (Qt plugins)
Отправлено: Dancing_on_water от Январь 05, 2013, 10:57
Теоретик? А ты попробуй. :)
И получишь от moc:
Error: Class contains Q_OBJECT macro but does not inherit from QObject

Не, просто лень вчера вечером было пробывать.  ;D

М-да, действительно вылетает. Значит мне не то помнится.


Название: Re: Система динамических расширений (Qt plugins)
Отправлено: lit-uriy от Январь 06, 2013, 13:10
mks, к выше сказанному добавлю - moc не понимает виртуального наследования, т.е. если класс является дважды наследником (хоть и не прямым) одного и того же класса, например, QObject-а.
Например:
class Interfase: public QObject ... (ради сигналов и слотов в интерфейсе)
class Target : public QWidget, public Interfase ... (собственно конечный класс)
при том, что
class QWidget : public QObject ...
т.е Terget дважды наследник QObject-а получается, вот это мета-объектный компилятор не съест.


Название: Re: Система динамических расширений (Qt plugins)
Отправлено: mks от Январь 06, 2013, 13:59
lit-uriy понятно. В случае из первого сообщения нет двойного наследования, наверно поэтому проблем и нет. Всем спасибо за дискуссию  :)