[solved] using two or three threads
-
Hey guys,
I have a gui that outputs a sine wave and square wave with user input frequency and amplitude. My code to produce both the square and sine wave is tested and works successfully.
My problem is: I have the sine wave working. I used threads to start and eliminate(from click of pushButtons) the generation of the sine wave. I am trying to do the same for the square wave, but when I click the pushButton, it generates the sine wave again.
I am not sure where I am going wrong. Any help would be appreciated. Code snippets below:wave.cpp:
@wave::wave(QWidget *parent) :
QMainWindow(parent),
ui(new Ui::wave)
{
ui->setupUi(this);
setup();
thread = new MyThread();
thread2 = new MyThread();}
wave::~wave()
{
delete ui;
delete thread;
delete thread2;
}void wave::on_pushButton_clicked()
{
//Generate
freq = ui->frequency->text().toDouble();
ampl = ui->amplitude->text().toDouble();
thread->start();
ui->pushButton->setEnabled(false);
ui->pushButton->setStyleSheet("background-color: gray");
ui->pushButton_2->setStyleSheet("background-color: rgb(255, 192, 192);"
"color: red;");
ui->pushButton_2->setEnabled(true);
}void wave::on_pushButton_2_clicked()
{
//Terminate
thread->terminate();
ui->pushButton_2->setEnabled(false);
ui->pushButton_2->setStyleSheet("background-color: gray");
ui->pushButton->setStyleSheet("background-color: rgb(192, 255, 208);"
"color: green;");
ui->pushButton->setEnabled(true);}
void wave::on_pushButton_3_clicked()
{
freq = ui->frequency->text().toDouble();
ampl = ui->amplitude->text().toDouble();
thread2->start();
ui->pushButton_3->setEnabled(false);
ui->pushButton_3->setStyleSheet("background-color: gray");
ui->pushButton_4->setStyleSheet("background-color: rgb(255, 192, 192);"
"color: red;");
ui->pushButton_4->setEnabled(true);
}void wave::on_pushButton_4_clicked()
{
thread2->terminate();
ui->pushButton_4->setEnabled(false);
ui->pushButton_4->setStyleSheet("background-color: gray");
ui->pushButton_3->setStyleSheet("background-color: rgb(192, 255, 208);"
"color: green;");
ui->pushButton_3->setEnabled(true);
}@wave.h:
@#ifndef WAVE_H
#define WAVE_H
#include "ui_wave.h"
#include <alsa/asoundlib.h>
#include <QMainWindow>
#include <QObject>
#include "mythread.h"namespace Ui {
class wave;
}class wave : public QMainWindow
{
Q_OBJECT
MyThread *thread;
MyThread *thread2;public:
explicit wave(QWidget *parent = 0);
~wave();private slots:
void on_pushButton_clicked();
void on_pushButton_2_clicked();void on_pushButton_3_clicked(); void on_pushButton_4_clicked();
private:
Ui::wave *ui;};
void onWriteLoopSine();
void onWriteLoopSquare();#endif // WAVE_H@
mythread.h:
@#ifndef MYTHREAD_H
#define MYTHREAD_H#include <QThread>
class MyThread : public QThread
{
Q_OBJECTprotected:
void run();public:
explicit MyThread(QObject *parent = 0);};
#endif // MYTHREAD_H@
mythread.cpp:
@#include "wave.h"
#include "mythread.h"MyThread::MyThread(QObject *parent) :
QThread(parent)
{
}void MyThread::run()
{
onWriteLoopSine();
onWriteLoopSquare();
}
@ -
You should tell the thread what kind of wave to use. You could use an enum for the wave types, or something.
This is a rough example that just uses a boolean flag to determine whether to use sine or not. I haven't tested it or anything.
in mythread.h:
@
protected:
void run();bool m_is_sine;
public:
explicit MyThread(QObject *parent = 0);
void setSine(bool useSine) { m_is_sine = useSine; }
@in mythread.cpp:
@MyThread::MyThread(QObject *parent) :
QThread(parent), m_is_sine(false)
{
}void MyThread::run()
{
if (m_is_sine)
onWriteLoopSine();
else
onWriteLoopSquare();
}
@in wave.cpp:
@
wave::wave(QWidget *parent) :
QMainWindow(parent),
ui(new Ui::wave)
{
ui->setupUi(this);
setup();
thread = new MyThread();
thread->setSine(true);
thread2 = new MyThread();
thread2->setSine(false);
}
@ -
Wow. Thanks alot again. I was just trying to use booleans, but i was doing it all wrong again.
This didn't quite work. The second thread which produces a square wave is producing square wave which run in the motion of sine waves. i'm checking my whole program again to see if there is anything wrong with it. -
[quote author="mlong" date="1313525638"]You should tell the thread what kind of wave to use. You could use an enum for the wave types, or something.
This is a rough example that just uses a boolean flag to determine whether to use sine or not. I haven't tested it or anything.
in mythread.h:
@
protected:
void run();bool m_is_sine;
public:
explicit MyThread(QObject *parent = 0);
void setSine(bool useSine) { m_is_sine = useSine; }
@in mythread.cpp:
@MyThread::MyThread(QObject *parent) :
QThread(parent), m_is_sine(false)
{
}void MyThread::run()
{
if (m_is_sine)
onWriteLoopSine();
else
onWriteLoopSquare();
}
@in wave.cpp:
@
wave::wave(QWidget *parent) :
QMainWindow(parent),
ui(new Ui::wave)
{
ui->setupUi(this);
setup();
thread = new MyThread();
thread->setSine(true);
thread2 = new MyThread();
thread2->setSine(false);
}
@[/quote]What if I had three threads, so I would need three conditions instead of 2?
-
The big picture is this...
You need some way to tell the thread what kind of wave to generate. Think of it as a property of the thread class.
I already suggested you could use an "enum":http://cplus.about.com/od/introductiontoprogramming/p/enumeration.htm to do it.
But figuring out how you want to do it is up to you.
-
Thanks mlong. I just included a second boolean.:)
Here's the solution:
mythread.cpp:
@#include "wave.h"
#include "mythread.h"MyThread::MyThread(QObject *parent) :
QThread(parent), is_sine(true), is_square(true)
{
}void MyThread::run()
{
if (is_sine) onWriteLoopSine();
else {
if(is_square) onWriteLoopSquare();
else onWriteLoopTri();
}
}@mythread.h:
@#ifndef MYTHREAD_H
#define MYTHREAD_H#include <QThread>
class MyThread : public QThread
{
Q_OBJECTprotected:
void run();
bool is_sine;
bool is_square;public:
explicit MyThread(QObject *parent = 0);
void setSine(bool useSine) { is_sine = useSine;}
void setSquare(bool useSquare) { is_square = useSquare;}};
#endif // MYTHREAD_H@
wave.cpp:
@wave::wave(QWidget *parent) :
QMainWindow(parent),
ui(new Ui::wave)
{
ui->setupUi(this);
setup();
sinethread = new MyThread();
sinethread->setSine(true);
squarethread = new MyThread();
squarethread->setSine(false);
squarethread->setSquare(true);
trithread = new MyThread();
trithread->setSine(false);
trithread->setSquare(false);}@