Глава 13. Создание графического интерфейса средствами Qt
Также нужно добавить к описанию класса (перед описанием любых других
членов класса в секции private) макрос Q_OBJECT, который будет обработан ме-
таобъектным компилятором moc (программа, которая выполняет предваритель-
ную обработку текста программы при запуске qmake и генерирует дополнитель-
ный код для реализации возможностей, которые предоставляет Qt). Далее в опи-
сании класса можно указать собственно сигналы и слоты. Сигналы описываются
в разделе signals, а слоты — в разделе slots, где перед названием раздела стоит
спецификатор доступа (public, private либо protected).
Слоты являются обычными методами класса, которые имеют реализацию
и могут принимать параметры и возвращать значения. Спецификатор досту-
па касается только использования слота как обычного метода но не сигнально-
слотовых соединений (при получении сигнала слот будет вызван независимо от
спецификатора). Также значения, которые возвращает слот, игнорируются при
сигнально-слотовом соединении. Сигналы, в отличие от слотов, не имеют реали-
зации. Их реализация обеспечивается метаобьектной системой Qt. Сигналы явля-
ются «защищёнными» (protected) методами — их можно посылать из классов,
которые наследуют от класса, содержащего сигнал. Сигнально-слотовые соеди-
нения могут происходить как между объектами, так и внутри самого объекта,
когда тот же объект является одновременно и отправителем сигнала и получа-
телем.
Создание собственных слотов и использования их в программе продемонстри-
руем на примере нашего предыдущего проекта. Добавим секцию private slots
и добавим описания слотов для обработки нажатия кнопки калькулятора.
private s l o t s :
void s l o t C l e a r ( ) ;
//Обработка нажатия кнопки сброса
void s l o t B u t t o n P r e s s e d ( i n t pNum) ; //Обработка цифровых кнопок
void s l o t P l u s E q u a l ( ) ; //Обработка кнопки сумирования/вывода результата
Для сохранения результата и слагаемого, добавим частный член класса:
private :
i n t mSum; //Результат
i n t mNextNumber ; //Следующее слагаемое
Для упрощения примера, наш калькулятор будет выполнять только одну опе-
рацию — сложение чисел от 0 до 9 с предыдущим результатом и вывод результата
при нажатии кнопки вывода результата и суммирования. Реализацию слотов до-
бавим в файл реализации класса CalculatorMainWindow.
void CalculatorMainWindow : : s l o t C l e a r ( )
{
lcdNumber−>d i s p l a y ( 0 ) ;
mSum = 0 ;
mNextNumber = 0 ;
}
void CalculatorMainWindow : : s l o t B u t t o n P r e s s e d ( i n t pNum)
{
mNextNumber = pNum ;
lcdNumber−>d i s p l a y (pNum) ;
}
void CalculatorMainWindow : : s l o t P l u s E q u a l ( )
{
mSum += mNextNumber ;
lcdNumber−>d i s p l a y (mSum) ;
Программирование на языке С++ в среде Qt Creator
13.5. Создание сигналов (signals) и слотов (slots)
369
mNextNumber = 0 ;
}
Теперь выполним соединения для кнопок суммирования и сброса в конструк-
торе класса.
c o n n e c t ( pushButtonC , SIGNAL( c l i c k e d ( ) ) , this , SLOT( s l o t C l e a r ( ) ) , Qt : :
UniqueConnection ) ;
c o n n e c t ( pushButtonPlus , SIGNAL( c l i c k e d ( ) ) , this , SLOT( s l o t P l u s E q u a l ( ) ) , Qt : :
UniqueConnection ) ;
Для реализации обработки цифровых кнопок можно использовать следующие
подходы:
• отдельные слоты для каждого случая
–
скорее всего будут содержать почти одинаковый код;
–
трудно поддерживать программный код;
–
трудно расширять возможности — требует ещё больше дополнитель-
ных слотов.
• наследовать кнопку и добавить дополнительный сигнал к классу, который
будет передавать значение
• дополнительный специализированный класс.
Однако возможен и другой подход — использование класса QSignalMapper.
QSignalMapper
привязывает некоторое значение к каждому сигналу и позволяет
избежать чрезмерного дополнительного создания слотов или специализирован-
ных классов. По сути, он выполняет роль посредника между объектами, которые
посылают сигналы, и слотом, который принимает параметр, изменяющийся в
зависимости от объекта, который его выполнил. Добавим описание нового поля
класса, содержащий указатель на QSignalMapper:
//Предварительное объявление классов
c l a s s QSignalMapper ;
. . .
private :
QSignalMapper ∗mMapper ;
В конструкторе класса создадим объект и свяжем каждую из кнопок с за-
данным для неё значением:
#include
. . .
mMapper = new QSignalMapper ( t h i s ) ;
c o n n e c t ( pushButton , SIGNAL( c l i c k e d ( ) ) , mMapper , SLOT(map ( ) ) , Qt : : UniqueConnection
) ;
c o n n e c t ( pushButton_2 , SIGNAL( c l i c k e d ( ) ) , mMapper , SLOT(map ( ) ) , Qt : :
UniqueConnection ) ;
c o n n e c t ( pushButton_3 , SIGNAL( c l i c k e d ( ) ) , mMapper , SLOT(map ( ) ) , Qt : :
UniqueConnection ) ;
c o n n e c t ( pushButton_4 , SIGNAL( c l i c k e d ( ) ) , mMapper , SLOT(map ( ) ) , Qt : :
UniqueConnection ) ;
c o n n e c t ( pushButton_5 , SIGNAL( c l i c k e d ( ) ) , mMapper , SLOT(map ( ) ) , Qt : :
UniqueConnection ) ;
c o n n e c t ( pushButton_6 , SIGNAL( c l i c k e d ( ) ) , mMapper , SLOT(map ( ) ) , Qt : :
UniqueConnection ) ;
c o n n e c t ( pushButton_7 , SIGNAL( c l i c k e d ( ) ) , mMapper , SLOT(map ( ) ) , Qt : :
UniqueConnection ) ;
c o n n e c t ( pushButton_8 , SIGNAL( c l i c k e d ( ) ) , mMapper , SLOT(map ( ) ) , Qt : :
UniqueConnection ) ;
© 2015 Алексеев Е. Р., Злобин Г. Г., Костюк Д. А., Чеснокова О. В., Чмыхало А. С.
370
Do'stlaringiz bilan baham: |