paceholder / nodeeditor

Qt Node Editor. Dataflow programming framework
BSD 3-Clause "New" or "Revised" License
2.94k stars 796 forks source link

Change amount of ports after a widget is created #315

Closed oddcitizenape closed 1 year ago

oddcitizenape commented 2 years ago

Hello guys, thank you for the great project! I've already figured out how to change the port datatype after a node widget is created. Now I would like to make the amount of ports customizeable on a new node widget. But just changing the way a registered model is behaving, doesn't seem to be enough so my widget always stays "portless" since I'm creating it with 0 ports and changing the amount of ports in the restore() method. Do you see any chance how I could accomplish this?

Here's how I'm tyring to handle my model right now:

QJsonObject QuestDBEffectModel::save() const
 {
    QJsonObject json;
    json["name"] = name();

    auto info = _widget->getPortInfo();
    QJsonObject ports;

    for (int x = 0; x < info.size(); ++x)
    {
        QJsonObject port;
        port["portName"] = info[x].first();
        port["portDataType"] = info[x].last();
        ports[QString::number(x)] = port;
    }

    json["ports"] = ports;

    return json;
}

void QuestDBEffectModel::restore(const QJsonObject &json)
{
    _json = json;

    QJsonObject ports = _json["ports"].toObject();
    _data.resize(ports.keys().count());

    for (int x = 0; x < _data.size(); ++x)
    {
        auto pdt = ports[QString::number(x)].toObject()["portDataType"].toString();
        ProMeFeMethods::castNodeDataPtrFromString(_data[x], ports[QString::number(x+1)].toObject()["portDataType"].toString());
        _widget->addPort(
                    ports[QString::number(x)].toObject()["portName"].toString(),
                    ports[QString::number(x)].toObject()["portDataType"].toString());
    }
}

unsigned int QuestDBEffectModel::nPorts(QtNodes::PortType portType) const
{
    return portType == PortType::In ? _data.size() : 0;
}

NodeDataType QuestDBEffectModel::dataType(QtNodes::PortType portType, QtNodes::PortIndex portIndex) const
{
    return _data.at(portIndex).get()->type();
}
paceholder commented 1 year ago

Now after the v3 branch has been merged you can do in your Node Model:

void QuestDBEffectModel::foo()
{
    Q_EMIT portsAboutToBeInserted(PortType::Out, // or PortType::In
                                  firstPortIndex,
                                  lastPortIndex);

    //   ... DO YOUR UNDERLYING DATA CHANGES HERE

    Q_EMIT portsInserted();
}

Let me know if something is not clear