Esempio n. 1
0
 void addTrees(const TreeList& trees) { _trees.insert(_trees.end(),trees.begin(),trees.end()); }
Esempio n. 2
0
RearrangeNodesCommand::RearrangeNodesCommand(const std::list<boost::shared_ptr<NodeGui> >& nodes,
                      QUndoCommand *parent)
: QUndoCommand(parent)
, _nodes()
{

    ///1) Separate the nodes in trees they belong to, once a node has been "used" by a tree, mark it
    ///and don't try to reposition it for another tree
    ///2) For all trees : recursively position each nodes so that each input of a node is positionned as following:
    /// a) The first non mask input is positionned above the node
    /// b) All others non mask inputs are positionned on the left of the node, each one separated by the space of half a node
    /// c) All masks are positionned on the right of the node, each one separated by the space of half a node
    ///3) Move all trees so that they are next to each other and their "top level" node
    ///(the input that is at the highest position in the Y coordinate) is at the same
    ///Y level (node centers have the same Y)
    
    std::list<NodeGui*> usedNodes;
    
    ///A list of Tree
    ///Each tree is a lit of nodes with a boolean indicating if it was already positionned( "used" ) by another tree, if set to
    ///true we don't do anything
    /// Each node that doesn't have any output is a potential tree.
    TreeList trees;
    
    for (std::list<boost::shared_ptr<NodeGui> >::const_iterator it = nodes.begin(); it!=nodes.end(); ++it) {
        const std::list<boost::shared_ptr<Natron::Node> >& outputs = (*it)->getNode()->getOutputs();
        if (outputs.empty()) {
            boost::shared_ptr<Tree> newTree(new Tree);
            newTree->buildTree(*it, usedNodes);
            trees.push_back(newTree);
        }
    }
    
    ///For all trees find out which one has the top most level node
    QPointF topLevelPos(0,INT_MAX);
    for (TreeList::iterator it = trees.begin(); it!=trees.end(); ++it) {
        const QPointF& treeTop = (*it)->getTopLevelNodeCenter();
        if (treeTop.y() < topLevelPos.y()) {
            topLevelPos = treeTop;
        }
    }
    
    ///now offset all trees to be top aligned at the same level
    for (TreeList::iterator it = trees.begin(); it!=trees.end(); ++it) {
        const QPointF& treeTop = (*it)->getTopLevelNodeCenter();
        QPointF delta(0,topLevelPos.y() - treeTop.y());
        if (delta.x() != 0 || delta.y() != 0) {
            (*it)->moveAllTree(delta);
        }
        
        ///and insert the final result into the _nodes list
        const std::list<TreeNode>& treeNodes = (*it)->getNodes();
        for (std::list<TreeNode>::const_iterator it2 = treeNodes.begin(); it2!=treeNodes.end(); ++it2) {
            NodeToRearrange n;
            n.node = it2->first;
            QSize size = n.node->getSize();
            n.newPos = it2->second - QPointF(size.width() / 2.,size.height() / 2.);
            n.oldPos = n.node->pos();
            _nodes.push_back(n);
        }
    }
    
    
    
}