예제 #1
0
파일: PortionDrawer.cpp 프로젝트: 8l/oovcde
void PortionDrawer::drawConnections(DiagramDrawer &drawer)
    {
    size_t lastColorIndex = NO_INDEX;
    for(auto const &conn : mGraph->getConnections())
        {
        GraphRect suppRect = getNodeRect(drawer, conn.mSupplierNodeIndex);
        GraphRect consRect = getNodeRect(drawer, conn.mConsumerNodeIndex);
        GraphPoint suppPoint;
        GraphPoint consPoint;
        drawer.getConnectionPoints(consRect, suppRect, consPoint, suppPoint);
        size_t colorIndex = conn.mSupplierNodeIndex;
        if(colorIndex != lastColorIndex)
            {
            if(lastColorIndex != NO_INDEX)
                {
                drawer.groupShapes(false, 0, 0);
                }
            Color lineColor = DistinctColors::getColor(colorIndex % DistinctColors::getNumColors());
            drawer.groupShapes(true, lineColor, Color(245,245,255));
            lastColorIndex = colorIndex;
            }
        drawArrowDependency(drawer, consPoint, suppPoint);
        }
    if(lastColorIndex != NO_INDEX)
        {
        drawer.groupShapes(false, 0, 0);
        }
    }
예제 #2
0
GraphSize OperationDrawer::drawOperation(DiagramDrawer &drawer, GraphPoint pos,
        OperationDefinition &operDef, const OperationGraph &graph,
        const OperationDrawOptions &options,
        std::set<const OperationDefinition*> &drawnOperations, bool draw)
    {
    std::vector<DrawString> drawStrings;

    if(draw)
        {
        drawer.groupShapes(true, Color(0,0,0), Color(245,245,255));
        }
    GraphSize size = drawOperationNoText(drawer, pos, operDef, graph, options,
            drawnOperations, drawStrings, draw);
    if(draw)
        {
        drawer.groupShapes(false, Color(0,0,0), Color(245,245,255));

        drawer.groupText(true, false);
        for(size_t i=0; i<drawStrings.size(); i++)
            {
            drawer.drawText(drawStrings[i].pos, drawStrings[i].str);
            }
        drawer.groupText(false, false);
        }
    return size;
    }
예제 #3
0
GraphSize OperationDrawer::drawDiagram(DiagramDrawer &drawer,
        OperationGraph &graph, const OperationDrawOptions &options)
    {
    drawer.setDiagramSize(getDrawingSize(drawer, graph, options));
    drawer.setCurrentDrawingFontSize(mDiagram.getDiagramBaseFontSize());
    return drawOrSizeDiagram(drawer, graph, options, true);
    }
예제 #4
0
static void drawCall(DiagramDrawer &drawer, GraphPoint source,
        GraphPoint target, bool isConst, int arrowLen)
    {
    drawer.drawLine(source, target, isConst);
    // Draw arrow
    if(source.x > target.x)
        arrowLen = -arrowLen;
    drawer.drawLine(GraphPoint(target.x-arrowLen, target.y-arrowLen),
            GraphPoint(target.x, target.y));
    drawer.drawLine(GraphPoint(target.x-arrowLen, target.y+arrowLen),
            GraphPoint(target.x, target.y));
    }
예제 #5
0
void OperationDrawer::drawLifeLines(DiagramDrawer &drawer,
        const std::vector<OperationClass> &classes,
        std::vector<int> const &classEndY, int endy)
    {
    drawer.groupShapes(true, Color(0,0,0), Color(245,245,255));
    endy += mCharHeight;
    for(size_t i=0; i<classes.size(); i++)
        {
        const auto &cl = classes[i];
        int x = cl.getLifelinePosX();
        drawer.drawLine(GraphPoint(x, classEndY[i]), GraphPoint(x, endy));
        }
    drawer.groupShapes(false, Color(0,0,0), Color(245,245,255));
    }
예제 #6
0
파일: PortionDrawer.cpp 프로젝트: 8l/oovcde
void PortionDrawer::updateNodePositions(DiagramDrawer &drawer)
    {
    if(mGraph)
        {
        if(mGraph->getNodes().size() != mNodePositions.size())
            {
            mNodePositions.resize(mGraph->getNodes().size());
            }
        std::vector<size_t> depths = getCallDepths();
        std::vector<int> columnPositions = getColumnPositions(drawer, depths);
        int yOffset = 0;
        const int margin = 20;
        int pad = static_cast<int>(drawer.getTextExtentHeight("W"));
        for(size_t i=0; i<mNodePositions.size(); i++)
            {
            GraphRect rect = getNodeRect(drawer, i);
            rect.start.y = yOffset;
            yOffset += pad + rect.size.y;
            rect.start.y += margin;
            rect.start.x = margin + columnPositions[depths[i]];
            mNodePositions[i] = rect.start;
            }
        }
#define PORTION_GENES 1
#if(PORTION_GENES)
    if(mNodePositions.size() > 0)
        {
        DiagramDependencyGenes genes;
        GraphRect rect = getNodeRect(drawer, 0);
        genes.initialize(*this, static_cast<size_t>(rect.size.y));
        genes.updatePositionsInDrawer();
        }
#endif
    }
예제 #7
0
파일: PortionDrawer.cpp 프로젝트: 8l/oovcde
void PortionDrawer::drawGraph(DiagramDrawer &drawer)
    {
    if(mGraph)
        {
        // This must be set for svg
        drawer.setDiagramSize(getDrawingSize(drawer));

        drawNodes(drawer);
        drawer.groupShapes(true, Color(0,0,0), Color(245,245,255));
        drawConnections(drawer);
        drawer.groupShapes(false, 0, 0);

        std::vector<DrawString> drawStrings;
        std::vector<bool> virtOpers;
        getNodeText(drawer, drawStrings, virtOpers);

        drawer.groupText(true, false);
        drawNodeText(drawer, false, drawStrings, virtOpers);
        drawer.groupText(false, false);

        drawer.groupText(true, true);
        drawNodeText(drawer, true, drawStrings, virtOpers);
        drawer.groupText(false, false);
        }
    }
예제 #8
0
파일: PortionDrawer.cpp 프로젝트: 8l/oovcde
void PortionDrawer::drawNodes(DiagramDrawer &drawer)
    {
    drawer.groupShapes(true, Color(0,0,0), Color(245,245,255));
    for(size_t i=0; i<mNodePositions.size(); i++)
        {
        if(mGraph->getNodes()[i].getNodeType() == PNT_Attribute)
            {
            drawer.drawRect(getNodeRect(drawer, i));
            }
        else
            {
            drawer.drawEllipse(getNodeRect(drawer, i));
            }
        }
    drawer.groupShapes(false, 0, 0);
    drawer.groupShapes(true, Color(0,0,255), Color(245,245,255));
    for(size_t i=0; i<mNodePositions.size(); i++)
        {
        if(mGraph->getNodes()[i].getNodeType() == PNT_NonMemberVariable)
            {
            drawer.drawRect(getNodeRect(drawer, i));
            }
        }
    drawer.groupShapes(false, 0, 0);
    }
예제 #9
0
파일: PortionDrawer.cpp 프로젝트: 8l/oovcde
void PortionDrawer::drawNodeText(DiagramDrawer &drawer, bool drawVirts,
    std::vector<DrawString> const &drawStrings, std::vector<bool> const &virtOpers)
    {
    for(size_t i=0; i<drawStrings.size(); i++)
        {
        if(drawVirts == virtOpers[i])
            {
            drawer.drawText(drawStrings[i].pos, drawStrings[i].str);
            }
        }
    }
예제 #10
0
GraphSize OperationDrawer::drawOrSizeDiagram(DiagramDrawer &drawer,
        OperationGraph &graph, const OperationDrawOptions &options, bool draw)
    {
    mCharHeight = static_cast<int>(drawer.getTextExtentHeight("W"));
    int pad = mCharHeight / 3;
    if(pad < 1)
        pad = 1;
    mPad = pad;

    GraphPoint startpos(mCharHeight, mCharHeight);
    GraphPoint pos = startpos;
    GraphSize size;
    GraphSize diagramSize;
    int maxy = 0;
    std::vector<int> classEndY;
    for(size_t i=0; i<graph.mOpClasses.size(); i++)
        {
        OperationClass &opClass = graph.mOpClasses[i];
        opClass.setPosition(pos);
        size = drawClass(drawer, opClass, options, draw);
        size_t condDepth = graph.getNestDepth(i);
        size.x += static_cast<int>(condDepth) * mPad;
        opClass.setSize(size);
        pos.x += size.x + mCharHeight;
        classEndY.push_back(startpos.y + size.y);
        if(size.y > maxy)
            maxy = size.y;
        }
    diagramSize.x = pos.x;

    pos = startpos;
    pos.y = startpos.y + maxy;  // space between class rect and operations
    std::set<const OperationDefinition*> drawnOperations;
    for(const auto &oper : graph.mOperations)
        {
        if(drawnOperations.find(oper) == drawnOperations.end())
            {
            size = drawOperation(drawer, pos, *oper, graph, options,
                    drawnOperations, draw);
            pos.y += size.y;
            }
        }
    if(draw)
        {
        drawLifeLines(drawer, graph.mOpClasses, classEndY, pos.y);
        }

    diagramSize.y = pos.y + mCharHeight;
    return diagramSize;
    }
예제 #11
0
파일: PortionDrawer.cpp 프로젝트: 8l/oovcde
void PortionDrawer::getNodeText(DiagramDrawer &drawer,
    std::vector<DrawString> &drawStrings, std::vector<bool> &virtOpers)
    {
    float textHeight = drawer.getTextExtentHeight("W");
    int pad = static_cast<int>(textHeight / 7.f * 2);
    int yTextOffset = static_cast<int>(textHeight) + pad;
    for(size_t i=0; i<mGraph->getNodes().size(); i++)
        {
        GraphRect rect = getNodeRect(drawer, i);
        rect.start.x += pad;
        rect.start.y += yTextOffset;
        PortionNode const &node = mGraph->getNodes()[i];
        drawStrings.push_back(DrawString(rect.start, node.getDisplayName().getStr()));
        virtOpers.push_back(node.isVirtualOperation());
        }
    }
예제 #12
0
void ComponentDiagram::updatePositionsInGraph(DiagramDrawer &nullDrawer)
    {
    ComponentDrawer drawer(*this, nullDrawer);
    int pad = nullDrawer.getPad(1) * 2;

    enum NodeVectorsIndex { NVI_ExtPackage, NVI_Lib, NVI_Exec, NVI_NumVecs };
    NodeVectors nodeVectors[NVI_NumVecs];
    int nodeSpacingY = 0;
    for(auto &node : mComponentGraph.getNodes())
        {
        GraphSize size = drawer.drawNode(node);
        node.setSize(size);
        if(nodeSpacingY == 0)
            nodeSpacingY = size.y * 2;
        if(node.getComponentNodeType() == ComponentNode::CNT_ExternalPackage)
            {
            nodeVectors[NVI_ExtPackage].add(&node, size.x, pad);
            }
        else
            {
            if(node.getComponentType() == ComponentTypesFile::CT_StaticLib)
                {
                nodeVectors[NVI_Lib].add(&node, size.x, pad);
                }
            else
                {
                nodeVectors[NVI_Exec].add(&node, size.x, pad);
                }
            }
        }
    int biggestX = 0;
    for(auto const &vec : nodeVectors)
        {
        if(vec.nodesSizeX > biggestX)
            biggestX = vec.nodesSizeX;
        }
    for(size_t veci=0; veci<sizeof(nodeVectors)/sizeof(nodeVectors[0]); veci++)
        {
        int yPos = static_cast<int>(veci) * nodeSpacingY;
        int xPos = (biggestX - static_cast<int>(nodeVectors[veci].nodesSizeX)) / 2;
        for(auto const &node : nodeVectors[veci].nodeVector)
            {
            node->setPos(GraphPoint(xPos, yPos));
            xPos += node->getRect().size.x + pad;
            }
        }
    }
예제 #13
0
GraphSize OperationDrawer::drawClass(DiagramDrawer &drawer, const OperationClass &node,
        const OperationDrawOptions & /*options*/, bool draw)
    {
    GraphPoint startpos = node.getPosition();
    const ModelType *type = node.getType();
    OovStringRef const typeName = type->getName();
    int rectx = 0;
    int recty = 0;
    const ModelClassifier *classifier = type->getClass();
    if(classifier)
        {
        if(draw)
            {
            drawer.groupText(true, false);
            }
        OovStringVec strs;
        std::vector<GraphPoint> positions;
        strs.push_back(typeName);
        splitStrings(strs, 30, 40);

        for(auto const &str : strs)
            {
            recty += mCharHeight + (mPad * 2);
            positions.push_back(GraphPoint(startpos.x+mPad, startpos.y + recty - mPad));
            int curx = static_cast<int>(drawer.getTextExtentWidth(str)) + mPad*2;
            if(curx > rectx)
                rectx = curx;
            }

        if(draw)
            {
            drawer.groupShapes(true, Color(0,0,0), Color(245,245,255));
            drawer.drawRect(GraphRect(startpos.x, startpos.y, rectx, recty));
            drawer.groupShapes(false, Color(0,0,0), Color(245,245,255));

            for(size_t i=0; i<strs.size(); i++)
                {
                drawer.drawText(positions[i], strs[i]);
                }
            drawer.groupText(false, false);
            }
        }
    return GraphSize(rectx, recty);
    }
예제 #14
0
GraphSize OperationDrawer::drawOperationNoText(DiagramDrawer &drawer, GraphPoint pos,
        OperationDefinition &operDef, const OperationGraph &graph,
        const OperationDrawOptions &options,
        std::set<const OperationDefinition*> &drawnOperations,
        std::vector<DrawString> &drawStrings, bool draw, int callDepth)
    {
    GraphPoint startpos = pos;
    // Add space between bottom of class and operation name
    int starty = startpos.y+(mPad*2);
    int y=starty;
    size_t sourceIndex = operDef.getOperClassIndex();
    int arrowLen = mCharHeight * 7 / 10;
    std::vector<int> condStartPosY;

    drawnOperations.insert(&operDef);
    const OperationClass &cls = graph.getClass(sourceIndex);
    if(callDepth == 0)
        {
        // Reinit all polys to initial conditions.
        mLifelinePolygons.clear();
        mLifelinePolygons.resize(graph.getClasses().size());
        }
    BlockPolygon &poly = mLifelinePolygons[sourceIndex];
    poly.setup(cls.getLifelinePosX(), mPad);

    if(!graph.isOperCalled(operDef))
        {
        // Show starting operation
        operDef.setRect(GraphPoint(cls.getPosition().x, y),
                GraphSize(mCharHeight*50, mCharHeight+mPad));
        y += mCharHeight;
        drawStrings.push_back(DrawString(GraphPoint(
                cls.getPosition().x, y), operDef.getName()));
        // Add space between operation name and called operations.
        y += (mPad * 2);
        int lineY = y + mPad*2;
        if(draw)
            {
            drawCall(drawer, GraphPoint(cls.getPosition().x, lineY),
                GraphPoint(cls.getLifelinePosX(), lineY),
                operDef.isConst(), arrowLen);
            }
        }
    for(const auto &stmt : operDef.getStatements())
        {
        int condOffset = poly.getDepth() * mPad;
        switch(stmt->getStatementType())
            {
            case ST_Call:
                {
                OperationCall *call = stmt->getCall();

                size_t targetIndex = call->getOperClassIndex();
                int lineY = y + mCharHeight + mPad*2;
                int sourcex = cls.getLifelinePosX();
                sourcex += condOffset;
                const OperationClass &targetCls = graph.getClass(targetIndex);
                int targetx = targetCls.getLifelinePosX();
                if(targetIndex == NO_INDEX)
                    {
                    // Handle [else]
//                  int len = mCharHeight*3;
//                  mDrawer.drawLine(GraphPoint(sourcex, lineY),
//                          GraphPoint(sourcex+len, lineY), call->isConst());
                    }
                else if(targetIndex != sourceIndex)
                    {
                    if(draw)
                        {
                        drawCall(drawer, GraphPoint(sourcex, lineY),
                            GraphPoint(targetx, lineY), call->isConst(), arrowLen);
                        }
                    }
                else
                    {
                    // Draw line back to same class
                    int len = mCharHeight*3;
                    int height = 3;
                    if(draw)
                        {
                        drawer.drawLine(GraphPoint(sourcex, lineY),
                            GraphPoint(sourcex+len, lineY), call->isConst());
                        drawer.drawLine(GraphPoint(sourcex+len, lineY),
                            GraphPoint(sourcex+len, lineY+height));
                        drawer.drawLine(GraphPoint(sourcex, lineY+height),
                            GraphPoint(sourcex+len, lineY+height), call->isConst());
                        }
                    y += height;
                    }
                int textX = (sourceIndex < targetIndex) ? cls.getLifelinePosX() :
                        targetCls.getLifelinePosX();
                GraphPoint callPos(textX+condOffset+mPad, y+mCharHeight);
                drawStrings.push_back(DrawString(callPos, call->getName()));
                call->setRect(GraphPoint(callPos.x, callPos.y-mCharHeight),
                        GraphSize(mCharHeight*50, mCharHeight+mPad));
                y += mCharHeight*2;

                // Draw child definition.
                OperationDefinition *childDef = graph.getOperDefinition(*call);
                if(childDef)
                    {
//                    poly.startChildBlock(condDepth, y);
                    if(drawnOperations.find(childDef) == drawnOperations.end())
                        {
                        poly.incDepth(y);
                        GraphSize childSize = drawOperationNoText(drawer,
                            GraphPoint(pos.x, y), *childDef, graph, options,
                            drawnOperations, drawStrings, draw, callDepth+1);
                        y += childSize.y + mPad * 2;
                        poly.decDepth(y);
                        }
                    else
                        {
                        // This draws a rectangle to signify that it is defined
                        // elsewhere in the diagram.
                        GraphRect rect(targetx + mPad*2, callPos.y + mPad*2,
                            mCharHeight+mPad, mCharHeight+mPad);
                        if(draw)
                            {
                            drawer.drawRect(rect);
                            }
                        y += mCharHeight+mPad;
                        }
//                    poly.endChildBlock(condDepth, y);
                    }
                }
                break;

            case ST_VarRef:
                {
                OperationVarRef *ref = stmt->getVarRef();

                size_t targetIndex = ref->getOperClassIndex();
                int lineY = y + mCharHeight + mPad*2;
                int sourcex = cls.getLifelinePosX();
                sourcex += condOffset;
                const OperationClass &targetCls = graph.getClass(targetIndex);
                int targetx = targetCls.getLifelinePosX();
                if(targetIndex == NO_INDEX)
                    {
                    int len = mCharHeight*3;
                    if(draw)
                        {
                        drawer.drawLine(GraphPoint(sourcex, lineY),
                            GraphPoint(sourcex+len, lineY), ref->isConst());
                        }
                    }
                else if(targetIndex != sourceIndex)
                    {
                    if(draw)
                        {
                        drawCall(drawer, GraphPoint(sourcex, lineY),
                            GraphPoint(targetx, lineY), ref->isConst(), arrowLen);
                        }
                    }
                else
                    {
                    // Draw line back to same class
                    int len = mCharHeight*3;
                    int height = 3;
                    if(draw)
                        {
                        drawer.drawLine(GraphPoint(sourcex, lineY),
                            GraphPoint(sourcex+len, lineY), ref->isConst());
                        drawer.drawLine(GraphPoint(sourcex+len, lineY),
                            GraphPoint(sourcex+len, lineY+height));
                        drawer.drawLine(GraphPoint(sourcex, lineY+height),
                            GraphPoint(sourcex+len, lineY+height), ref->isConst());
                        }
                    y += height;
                    }
                int textX = (sourceIndex < targetIndex) ? cls.getLifelinePosX() :
                        targetCls.getLifelinePosX();
                GraphPoint callPos(textX+condOffset+mPad, y+mCharHeight);
                if(draw)
                    {
                    drawStrings.push_back(DrawString(callPos, ref->getName()));
                    }
                ref->setRect(GraphPoint(callPos.x, callPos.y-mCharHeight),
                        GraphSize(mCharHeight*50, mCharHeight+mPad));
                y += mCharHeight*2;
                }
                break;

            case ST_OpenNest:
                {
                GraphPoint lifePos(cls.getLifelinePosX()+condOffset+
                        mPad, y+mCharHeight);
                const OperationNestStart *cond = stmt->getNestStart();
                if(draw)
                    {
                    drawStrings.push_back(DrawString(lifePos, cond->getExpr()));
                    }
                condStartPosY.push_back(y);
                y += mCharHeight*2;

                poly.incDepth(y);
                }
                break;

            case ST_CloseNest:
                {
                poly.decDepth(y);
                }
                break;
            }
        }
    if(callDepth == 0)
        {
        for(auto &poly : mLifelinePolygons)
            {
            poly.finishBlock();
            if(draw)
                {
                drawer.drawPoly(poly, Color(245,245,255));
                }
            }
        }

    return GraphSize(0, y - startpos.y);
    }