Russian Qt Forum
Ноябрь 24, 2024, 10:34 *
Добро пожаловать, Гость. Пожалуйста, войдите или зарегистрируйтесь.
Вам не пришло письмо с кодом активации?

Войти
 
  Начало   Форум  WIKI (Вики)FAQ Помощь Поиск Войти Регистрация  

Страниц: [1]   Вниз
  Печать  
Автор Тема: Сигналы и Слоты в Плагинах Qt  (Прочитано 10881 раз)
chipset
Гость
« : Май 31, 2007, 11:36 »

Здравствуйте, не подскажите есть ли возможность посылать и получать сигналы в плагин и наоборот в главную программу? ...
Записан
QCasper
Гость
« Ответ #1 : Май 31, 2007, 13:49 »

Здравствуйте, есть.
Записан
chipset
Гость
« Ответ #2 : Май 31, 2007, 14:15 »

Цитата: "QCasper"
Здравствуйте, есть.

не дадите пример... или куда глЯдеть?
Записан
QCasper
Гость
« Ответ #3 : Май 31, 2007, 16:04 »

Цитата: "chipset"
Цитата: "QCasper"
Здравствуйте, есть.

не дадите пример... или куда глЯдеть?


Я сделал так: создал класс, наследованный от интерфейса, который виден и плагину и приложению. Методы класса - сигналы/слоты. В самом плагине есть метод, который возвращет указатель на объект класса. Вот через него все и происходит. Типа такого:

Код:

class INotifyer {
   virtual ~INotifyer() {}

   virtual void someSignal() = 0;
   virtual void someSlot() = 0;
};
class Notifyer : public QObject, public INotifyer {
   Q_OBJECT

signals:
   virtual void someSignal() = 0;

public slots:
   virtual void someSlot() = 0;
};
class IPlugin {
   virtual ~IPlugin() {}
   virtual INotifyer* notifyer() = 0;
};
class Plugin : public IPlugin {
   Q_OBJECT
   Q_INTERFACES(IPlugin)
public:
   INotifyer* notifyer() {
      if (!m_Notifyer)
         m_Notifyer = new Notifyer();
      return m_Notifyer;
   }
private:
   Notifyer *m_Notifyer;
};


далее внутри плагина сигнал можно сэмитить так:
Код:
emit m_Notifyer->someSignal()


в приложении сигнал обрабатывается так:
Код:
connect(plugin->notifyer(), SIGNAL(someSignal()), this, SLOT(applicationSlot()));

где plugin - указатель на корневой объект плагина.

вроде ниче не забыл...
Записан
chipset
Гость
« Ответ #4 : Июнь 01, 2007, 09:32 »

to QCasper:
не получается ... Грустный
In member function ‘virtual INotifyer* Plugin::notifyer()’:
../../plugandpaint/interfaces.h:93: error: cannot allocate an object of abstract type ‘Notifyer’
../../plugandpaint/interfaces.h:74: note:   because the following virtual functions are pure within ‘Notifyer’:
../../plugandpaint/interfaces.h:77: note:       virtual void Notifyer::someSignal()
../../plugandpaint/interfaces.h:80: note:       virtual void Notifyer::someSlot()
../../plugandpaint/interfaces.h:77: note:       virtual void Notifyer::someSignal()
../../plugandpaint/interfaces.h:80: note:       virtual void Notifyer::someSlot()


92      if (!m_Notifyer)
93         m_Notifyer = new Notifyer();
94      return m_Notifyer;

в чём подвох? Использую Qt4.4
Записан
Steven_Orko
Гость
« Ответ #5 : Июнь 01, 2007, 10:27 »

Цитата: "chipset"

в чём подвох?


В том, что ты переписал код не глядя. Хоть бы разобрался.
В коде, приведенном QCasper, используются чисто виртуальные (pure virtual) члены-функции. А класс с такими членами считается абстрактным, и создать экземпляр такого класса нельзя.
Записан
chipset
Гость
« Ответ #6 : Июнь 01, 2007, 15:41 »

я начинающий.... подскажите, плиз

добавлено спустя 4 часа 27 минут:

 спасибо за подсказки.. но не удаётся... попробывал различные варианты..
пример скомпилился, но плагин не работает...

добавлено спустя 39 минут:

 если присутствует в коде строчка QPushButton quit("Quit", &window); плагин перестаёт грузится, если строчку убрать ... то плагин грузится, но не работает....
ниукого нет готового примера с применением сигналов и слотов....
Записан
Lion
Гость
« Ответ #7 : Июнь 01, 2007, 20:15 »

Сигналы и слоты работают только в наследниках QObject и для подключения нужна ссылка на QObject, для этого в интерфейс (INotifyer) надо поместить функцию возвращающую ссылку на Notifyer как на QObject:
Код:
virtual QObject *instance() = 0;

А в Notifyer:
Код:
virtual QObject *instance() { return this; }

В приложени сигнал обрабатывается так:
Код:
connect(plugin->notifyer()->instance(), SIGNAL(someSignal()), this, SLOT(applicationSlot()));


Пример приведенный QCasper работать не будет т.к. plugin->notifyer() возвращает ссылку на INotifyer*, которая не может быть приведена к QObject* и функция connect() выдаст ошибку.
Записан
QCasper
Гость
« Ответ #8 : Июнь 01, 2007, 21:39 »

Цитата: "Lion"
Сигналы и слоты работают только в наследниках QObject

Пример приведенный QCasper работать не будет т.к. plugin->notifyer() возвращает ссылку на INotifyer*, которая не может быть приведена к QObject* и функция connect() выдаст ошибку.


Да, я ошибся немного, в таком виде как я привел, конструкция действительно работать не будет. На самом деле интерфейс INotifyer я наследую от QObject, и потом уже при объявлении класса Notifyer можно обойтись без множественного наследования:

Код:
class INotifyer : public QObject {
   virtual ~INotifyer() {}

   virtual void someSignal() = 0;
   virtual void someSlot() = 0;
};
class Notifyer : public INotifyer {
   Q_OBJECT

signals:
   void someSignal();

public slots:
   void someSlot();
};


Как вариант, можно использовать конструкцию, предлагаемую Lion'ом, но моя получается короче (в плане кодописанины) при соединении Подмигивающий
Код:
connect(plugin->notifyer(), SIGNAL(someSignal()), this, SLOT(applicationSlot()));

vs
Код:
connect(plugin->notifyer()->instance(), SIGNAL(someSignal()), this, SLOT(applicationSlot()));
Записан
Страниц: [1]   Вверх
  Печать  
 
Перейти в:  


Страница сгенерирована за 0.049 секунд. Запросов: 21.