В.б. Реализация задуманного функционала

Рассмотрим тот набор функционала, который мы учли в структуре меню:

I. Фаил

  1. Создать name = «Creat_act»
  2. Открыть name = «Open_act»
  3. Сохранить тескт name = «Save_act»
  4. Сохранить фонему name = «Save_fonem_act»
  5. Выход name = «Exit_act»

II Правка

  1. Отменить name = «Undo_act»
  2. Вернуть name = «Redo_act»
  3. Тут сделаем разделитель name = «separator»
  4. Копировать name = «Copy_act»
  5. Вставить name = «Past_act»
  6. Вырезать name = «Cut_act»
  7. Очистить name = «Clear_act»
  8. Разделитель name = «separator»
  9. Выделить все name = «SelectAll_act»
  10. Найти name = «Find_act»

III Параметры

  • Удалить не читаемые символы name = «find_char»

IV О программе

  • Об авторе name = «about_act»

При программировании графического интерфейса пользователя часто необходимо сообщать одним элементам об изменении других элементов управления. То есть надо обеспечить связь между объектами любых видов. Например, если пользователь нажимает кнопку Close необходимо, чтобы была вызвана функция окна close(). В библиотеке Qt для связи между объектами используются механизм сигналов и слотов.  В такой терминологии слот – это функция, вызываемая в ответ на определенный сигнал, который испускается, когда происходит определенное событие. Сигналы и слоты связаны не жёстко: Класс, испускающий сигналы, не знает и не интересуется, который из слотов получит сигнал.

Для большинства пунктов меню потребуется предварительно создать слот, который будет «вызываться» при нажатии на пункт. Однако для некоторых пунктов уже есть стандартные слоты и сигналы. Для связи таких слотов и сигналов в режиме «Дизайнера» имеется инструмент называемый Редакторе сигналов и слотов (4). Первое что мы реализуем, используя этот редактор будет действие соответствующее пункту «Выход». Для этого в Редакторе сигналов и слотов (4) добавим нажатием зеленого плюса  строку. Заполним следующие поля получившейся записи используя выпадающие списки: отправитель – Exit_act, (это имя пункта меню);  сигнал – triggered(); получатель -  Golos; слот – close(). После выполнения компилирования и запуска программы в режиме отладка (debug) выбрав в меню пункт «Выход» программа закроется.  Хорошее начало реализации задуманного функционала.

Аналогично действуя в Редакторе сигналов и слотов создается функционал для работы в текстовом поле.  На рисунке ниже представлен окончательный вид Редактора сигналов и слотов.


Теперь нам потребуется создать слоты для реализации остальных пунктов меню. Перейдем в режим редактора путем нажатия на пиктограмму»Редактор» – она располагается над пиктограммой «Дизайнер». Теперь на боковой панели в древовидной схеме проекта выберем заголовочный фаил golos.h.  В окне текстового редактора отобразится автоматически сгенерированное содержимое заголовочного фаила. Добавим в конец class Golos : public QMainWindow секцию private slots:

private slots:
 void open_file();
 void creat_file();
 void about_file();
 void find_file();
 void save_file();

После этого откроем для редактирования фаил исходных текстов golos.cpp и запрограммируем перечисленные выше слоты, как это делается с функциями.

//Создание файла приравниваем к простой очистке текстового поля и
// переменной, хранящей имя файла.
void Golos::creat_file()
{
  TextFileName.clear();
  ui->RechText->clear();
}
//открытие файла
//чтобы избежать проблем с кодировкой текст
//обрабатывается в QString::fromUtf8()
void Golos::open_file()
{
TextFileName = QFileDialog::getOpenFileName(this,
QString::fromUtf8("Открыть фаил"), QDir::currentPath());
if (!TextFileName.isEmpty()) {
//не придумал что добавить еще чтобы выполнилось след. условие,
//поэтому написал это
TextFileName = TextFileName;
 if (TextFileName.isNull()){
  QMessageBox::information(this, tr("Golos"),
  QString::fromUtf8("невозможно открыть %1.").arg(TextFileName));
 }
}
 QFile inputFile(TextFileName);
 inputFile.open(QIODevice::ReadOnly);
 QTextStream in(&inputFile);
 QString line = in.readAll();
 inputFile.close();
 ui->RechText->setPlainText(line);
}

//сохранение файла
void Golos::save_file()
{
if (TextFileName.isEmpty()) {
 TextFileName = QFileDialog::getSaveFileName(this,
          QString::fromUtf8("Сохранить фаил"), QDir::currentPath(),
                                              "Text files (*.txt)");

}
 QFile file(TextFileName);
 if (!file.open(QIODevice::WriteOnly)) {
  QMessageBox::information(this, QString::fromUtf8("Golos"),
              QString::fromUtf8("Запись в фаил %1 не возможна.").
                                                arg(TextFileName));
 }
 QFile outFile(TextFileName);
 outFile.open(QIODevice::WriteOnly);
 outFile.write(ui->RechText->toPlainText().trimmed().toUtf8());
 outFile.close();
}
//при нажатии на пункт меню "о программе" откывается сайт проекта -
//это не лучший подход т.к. в отсутствии интернета пользователь
//не получит информацию
void Golos::about_file()
{
 if(!QDesktopServices::openUrl(QUrl(
               QString::fromUtf8("http://golos.sourceforge.net/"))))
 {
  QMessageBox::information(
  QApplication::activeWindow(),
  QApplication::applicationName(),
  QString::fromUtf8("Невозможно открыть сведения о программе.
                Перейдите на сайт http://golos.sourceforge.net/"));
 }
}

//для поиска в тексте используем QInputDialog
void Golos::find_file()
{
 bool ok;
 QString text = QInputDialog::getText(this,
                             QString::fromUtf8("Найти"),
                             QString::fromUtf8("Найти:"),
                             QLineEdit::Normal,
                             QString::fromUtf8(""), &ok);
  if (!(text.isEmpty() or text.isNull())){
    if (!ui->RechText->find(text, QTextDocument::FindWholeWords)){
      QMessageBox::information(this, QString::fromUtf8("Golos"),
      QString::fromUtf8(" \"%1\" не найдено.").arg(text));
       }
   }
}

Теперь требуется соединить сигналы с задуманными слотами используя QObject::connect() и макросы SIGNAL() и SLOT(), ниже приведен листинг некоторых слотов Golos.

Golos::Golos(QWidget *parent) :
 QMainWindow(parent),
ui(new Ui::Golos)
{
ui->setupUi(this);

//hot key for Open and slot
ui->Open_act->setShortcut(tr("Ctrl+O"));

connect(ui->Open_act, SIGNAL(triggered()), this, SLOT(open_file()));
ui->Save_act->setShortcut(tr("Ctrl+S"));
connect(ui->Save_act, SIGNAL(triggered()), this, SLOT(save_file()));
ui->Creat_act->setShortcut(tr("Ctrl+N"));
connect(ui->Creat_act, SIGNAL(triggered()), this,
                                                SLOT(creat_file()));

//Поиск Golos::find_file()
ui->about_act->setShortcut(tr("Cntr+F"));
connect(ui->Find_act, SIGNAL(triggered()), this, SLOT(find_file()));
ui->about_act->setShortcut(tr("F1"));
connect(ui->about_act, SIGNAL(triggered()), this,
                                                SLOT(about_file()));

}

В листенге выше функция setShortcut() используется для указания горячих клавиш тем объектам, которым не удалось это сделать на шаге разработки формы в Редакторе действий (4) .

Чтобы все функции заработали требуется подключить некоторые библиотеки:

//Вывод сообщений приложения
#include <QMessageBox>

//используется функция из этой библиотеки для ввода фразы для поиска
#include <QInputDialog>

//функции этой библиотеки используются при открытии файла
#include "QTextStream"

//требуется для "о программе"
#include "QDesktopServices"
#include "QUrl"
//используется для в диалогах действия с файлами
#include "QFileDialog"

Реализацию пункта «Сохранить фонему» и «Удалить не читаемые символы» отложим до момента разработки синтеза речи.

Статья на стадии разработки

Добавить комментарий