这是一个SpinBox的示例,它将其更改写入基础变量。构建窗口小部件时,我调用的主要问题是valueChanged。有没有更优雅的方式来做到这一点?我认为将小部件与自身连接起来很奇怪,但valueChanged不是虚拟的。

class ValueWriterInt: public QSpinBox {
    Q_OBJECT

public:
    ValueWriterInt(vector<int*> const& value): myValue(value) { 
        QObject::connect(this, SIGNAL(valueChanged(int)), this, SLOT(valueChanged(int)));
    }
    ~ValueWriterInt() {}

private slots:
    void    valueChanged(int new_value) {
        for (auto it = myValue.begin(); it != myValue.end(); ++it)
            **it = new_value;
    }

private:
    vector<int*>        myValue;
};
有帮助吗?

解决方案

我看到什么特别怪异围绕插件连接到其自身。有一种检测和响应数据更新的方法实际上听起来是件好事,因为您在调试时检查失败的次数较少。在您的具体情况下,它会导致一些不良行为,但一般来说这是一个很好的解决方案。

现在,我已经表达了一种认为反身联系本身并不优雅的观点,我将建议一种不那么“优雅”的联系。解决方案,以防止在构造之后调用 valueChanged 。您可以使用一个标志来确定对象是否刚刚构造并提前返回以防止代码在构造后立即运行。在您的示例中:

class ValueWriterInt: public QSpinBox {
Q_OBJECT

public:
    ValueWriterInt(vector<int*> const& value): myValue(value), myAfterInit(true) { 
        QObject::connect(this, SIGNAL(valueChanged(int)), this, SLOT(valueChanged(int)));
    }
    ~ValueWriterInt() {}

private slots:
    void        valueChanged(int new_value) {
        if (myAfterInit) {
            myAfterInit = false;
            return;
        }
        for (auto it = myValue.begin(); it != myValue.end(); ++it)
                **it = new_value;
    }

private:
    vector<int*>                myValue;
    boolean                     myAfterInit;
};

这是不是太糟糕的溶液。它将至少为您提供所需的行为,直到(以及如果)您可以找到更优雅的方法。

其他提示

那么你想在这里完成什么?是的,valueChanged不是虚拟的 - 为什么它应该是,你的对象应该直接将他们自己的插槽连接到他们想要响应的任何信号,不是吗?

除了使用SIGNAL-SLOT连接之外别无他法。但是,我会更改插槽的名称,因此它与信号名称不同。

即使没有完成连接,如何调用插槽也很有趣。我怀疑更改插槽名称可以解决这个问题。

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top