线程运行时错误 - 无法从另一个线程停止Qt定时器 - MinGW

时间:2016-07-20 15:31:41

标签: c++ multithreading qt mingw qtimer

我有一个在Qt 5.7和Qt Creator中创建的GUI应用程序,其中两个按钮在代码中调用两个不同的函数: 在MainWindow构造函数中:

connect(button1, SIGNAL(buttonClickedForBattle(Ally*,Enemy&)), this, SLOT(attack(Ally*,Enemy&)));
connect(button2, SIGNAL(buttonClickedForBattle(Ally*,Enemy&)), this, SLOT(fire(Ally*,Enemy&)));

我的两个插槽完全相同,只是内部的一个小函数调用(计算损坏)不同,触发时声音不同。

问题仅发生在“火”插槽中,如下所示:

void MainWindow::fire(Ally *a, Enemy &e)
{
    ...
    sound->play();
    ...

    system.fira(*a, e); // calculates and applies damage

    if(e.getHP() == 0)
    {
        ...
    }
    else
    {
        timer1 = new MyTimer("PrepareCounterAttackTimer", e, a);
        connect(timer1, SIGNAL(timeoutNowAttack(Enemy&,Ally*)), timer1, SLOT(stopAndBlock2(Enemy&,Ally*)));
        connect(timer1, SIGNAL(timeoutNowAttack(Enemy&,Ally*)), this, SLOT(PrepareCounterAttack(Enemy&,Ally*)));
        timer1->start(2000);
        cout << "timer started" << endl;
    }

程序执行整个功能(出现“定时器启动”),但从未到达“timer1”的末尾,因此它永远不会进入“PrepareCounterAttack”插槽。另一个插槽用于停止定时器和阻塞信号(之后我使用其他定时器);删除它的行不会改变结果。执行时,单击“button2”时,GUI上方会立即显示一个弹出窗口:

Runtime Error!
R6016 
- not enough space for thread data

当我点击“确定”时,我得到以下输出:

QObject::~QObject: Timers cannot be stopped from another thread

仅供参考,此计时器的类型为“MyTimer”,它是QTimer的子类: 头文件:

class MyTimer : public QTimer
{
   Q_OBJECT

public:
   MyTimer();
   MyTimer(std::string name, Enemy & en, Ally* al);
   ~MyTimer();

private:
   std::string name;
   Ally* ally;
   Enemy enemy;

signals:
   void mytimeout();
   void timeoutNowAttack(Enemy & en, Ally* al);

public slots:
   void stopAndBlock();

protected:
   void timerEvent(QTimerEvent* e);
};

Cpp文件:

MyTimer::MyTimer()
        :QTimer()
    {
        setSingleShot(true);
    }

    MyTimer::MyTimer(string n, Enemy & en, Ally* al)
        :QTimer()
    {
        setSingleShot(true);
        name = n;
        ally = al;
        enemy = en;
    }

    MyTimer::~MyTimer()
    {
    }

    void MyTimer::timerEvent(QTimerEvent* e)
    {
        if(e->timerId() == this->timerId())
        {
            emit mytimeout();
            emit timeoutNowAttack(enemy, ally);
        }
    }

    void MyTimer::stopAndBlock()
    {
        blockSignals(true);
        stop();
    }

我不明白的是:

  • 为什么我从未明确创建过一个线程问题?
  • 为什么要调用QObject析构函数?
  • 如何在 button2 的插槽中发生运行时错误,但不在 button1的的? if / else部分字面意思相同!

我不擅长多线程,这是我的第一个大型Qt计划。

重要提示:

中出现问题
  • Windows(在Linux上,一切都很好)
  • 32位MinGW(当我切换到64位MSVC 2013时,插槽执行到最后)

是32位还是64位问题? 谢谢你的任何想法。

0 个答案:

没有答案