示例#1
0
    def addCircleOverlay(self, circleOverlay, container=True, **attr):
        """Adds and returns fig.Circle for all circles of the given
        overlay, using the overlays' color and width."""

        if container == True:
            container = self.f

        circles = circleOverlay.originalCircles
        attr = dict(attr)
        self._setOverlayColor(circleOverlay, "penColor", attr)

        o = self.offset + attr.get('offset', (0, 0))
        if self.roi:
            o = o - self.roi.begin()  # don't modify in-place!

        result = fig.Compound(container)
        for center, radius in circles:
            if self.roi and not self.roi.contains(center + o):
                continue
            p = intPos(((center[0], center[1]) + o) * self.scale)
            dc = fig.Circle(p, radius * self.scale)
            for a in attr:
                setattr(dc, a, attr[a])
            result.append(dc)

        return result
示例#2
0
    def addPointCircles(self,
                        points,
                        radius,
                        returnIndices=False,
                        container=True,
                        **attr):
        """fe.addPointCircles(points, radius, returnIndices = False,...)

        Marks each point in points with a circle of the given radius
        (in pixels) if it is within the clipping rect.  The list of
        fig.Circle objects is returned.  Again, note the possibility
        of setting properties (depth, penColor, lineStyle, lineWidth,
        ...) on all resulting objects via keyword arguments
        (cf. documentation of the FigExporter class).

        By default, circles will be filled, but have lineWidth=0.
        To draw a transparent circle, call:

        fi.addPointCircles([(5.2,5.3)], 2, penColor=fig.Color.Cyan,fillStyle=fig.FillStyle.None,lineWidth=1)

        If returnIndices is set to True (default: False), a list of
        (i, c) pairs is returned instead, where c is the fig.Circle
        object, and i is the index of the corresponding position in
        points."""

        if container == True:
            container = self.f

        attr = dict(attr)
        if "fillStyle" not in attr:
            attr["fillStyle"] = fig.FillStyle.Solid
        if "lineWidth" not in attr and attr["fillStyle"] != fig.FillStyle.None:
            attr["lineWidth"] = 0

        compound = fig.Compound(container)
        if returnIndices:
            result = []
        else:
            result = compound

        o = self.offset + attr.get('offset', (0, 0))
        o2 = self.roi and o - self.roi.begin() or o
        for i, point in enumerate(points):
            if self.roi:
                radiusOff = (radius, radius)
                circleBounds = BoundingBox(o + point - radiusOff,
                                           o + point + radiusOff)
                if not self.roi.contains(circleBounds):
                    continue  # FIXME: add arcs if intersects
            p = intPos((numpy.array((point[0], point[1])) + o2) * self.scale)
            dc = fig.Circle(p, radius * self.scale)
            for a in attr:
                if a != "offset":
                    setattr(dc, a, attr[a])
            if returnIndices:
                result.append((i, dc))
            compound.append(dc)

        return result
示例#3
0
    def addPixelRaster(self,
                       rect=None,
                       labels=None,
                       fill=None,
                       container=True,
                       labelType=int,
                       **attr):
        """The default label size looks good with 1cm^2 pixels
        (scale = 450)."""

        assert rect or labels or fill
        if rect is None:
            rect = Rect2D((labels or fill).size())
        elif not hasattr(rect, "upperLeft"):
            w, h = rect
            rect = Rect2D((w, h))

        if container == True:
            container = self.f
        result = fig.Compound(container)

        for x, y in meshIter(rect):
            boxX1 = (x - rect.left()) * self.scale
            boxY1 = (y - rect.top()) * self.scale
            boxX2 = boxX1 + self.scale
            boxY2 = boxY1 + self.scale

            pixelRect = fig.PolyBox(boxX1, boxY1, boxX2, boxY2)
            for a in attr:
                setattr(pixelRect, a, attr[a])

            if labels:
                textX = (boxX1 + boxX2) / 2
                textY = (boxY1 + boxY2) / 2

                label = fig.Text(fig.Vector(textX, textY),
                                 str(labelType(labels[x, y])),
                                 alignment=fig.Alignment.Centered)
                label.pos += (0, label.height / 2)

                label.depth = pixelRect.depth - 10
                label.font = fig.Font.Helvetica
                result.append(label)

            if fill:
                pixelRect.fillStyle = fig.FillStyle.Solid
                pixelRect.fillColor = self.f.getColor(int(fill[x, y]))

            result.append(pixelRect)
        return result
示例#4
0
    def addEdgels(self, edgels, length=0.65, container=True, **attr):
        if container == True:
            container = self.f

        result = fig.Compound(container)

        for edgel in edgels:
            pos = numpy.array((edgel.x, edgel.y))
            c = math.cos(edgel.orientation) * length / 2
            s = -math.sin(edgel.orientation) * length / 2
            self.addClippedPoly([pos + (c, s), pos - (c, s)],
                                container=result,
                                **attr)

        return result
示例#5
0
    def addEdgeOverlay(self, edgeOverlay, container=True, **attr):
        """Adds and returns fig.Polygon for all edges (or -parts, see
        addClippedPoly) of the given overlay, using the overlays'
        color."""

        if container == True:
            container = self.f

        edges = edgeOverlay.originalEdges
        attr = dict(attr)
        self._setOverlayColor(edgeOverlay, "penColor", attr)
        attr["offset"] = (edgeOverlay.offset[0] - 0.5,
                          edgeOverlay.offset[1] - 0.5)

        result = fig.Compound(container)
        for edge in edges:
            parts = self.addClippedPoly(edge, container=result, **attr)
        return result
示例#6
0
    def addMapEdges(self,
                    map,
                    skipBorder=False,
                    returnEdges=False,
                    container=True,
                    **attr):
        """Adds and returns fig.Polygons for all map edges (or -parts,
        see addClippedPoly).  If no penColor is given, only edges with
        a valid 'color' attribute are exported (can be either a fig or
        a Qt color).

        For example, to draw only a subregion, and shift the upper left of
        the region to the origin, call

        fi.addMapEdges(map, penColor=fig.Color.Green, \
             offset=(-13,-13), roi=BoundingBox((13,13), (24,24)))

        """

        if container == True:
            container = self.f

        compound = fig.Compound(container)
        if returnEdges:
            result = []
        else:
            result = compound

        for edge in map.edgeIter():
            if skipBorder and edge.flag(flag_constants.BORDER_PROTECTION):
                continue
            parts = self.addClippedPoly(edge, container=compound, **attr)
            if returnEdges:
                result.extend([(edge, part) for part in parts])

        return result
示例#7
0
    def addMapFaces(self,
                    geomap,
                    faceMeans=None,
                    similarity=None,
                    returnFaces=False,
                    container=True,
                    **attr):
        """fe.addMapFaces(geomap, faceMeans, ...)

        Adds and returns fig.Polygons for all map faces (or -parts,
        see addClippedPoly).  Clipping closed polygons should work
        nowadays, too."""

        import maputils

        def getGray(face):
            faceColor = faceMeans[face.label()]
            return self.f.gray(int(faceColor))

        def getRGB(face):
            faceColor = faceMeans[face.label()]
            return self.f.getColor(map(int, tuple(faceColor)), similarity)

        if not faceMeans:
            if not hasattr(geomap, "faceMeans"):
                raise ValueError(
                    "addMapFaces: need faceMeans for proper coloring")
            faceMeans = geomap.faceMeans

        if hasattr(faceMeans, "bands"):
            getFaceColor = getGray
            if faceMeans.bands() == 3:
                getFaceColor = getRGB
        else:
            getFaceColor = lambda face: faceMeans[face.label()]

        if container == True:
            container = self.f

        attr = dict(attr)
        attr["lineWidth"] = attr.get("lineWidth", 0)
        attr["fillStyle"] = attr.get("fillStyle", fig.FillStyle.Solid)

        compound = fig.Compound(container)
        if returnFaces:
            result = []
        else:
            result = compound

        todo = [geomap.face(0)]
        # +1 because the first iteration will not add any objects:
        currentDepth = attr.get("depth", 100) + 1
        while todo:
            thisLayer = todo
            todo = []
            for face in thisLayer:
                if face.area() > 0:
                    color = getFaceColor(face)
                    if color is not None:
                        thisattr = dict(attr)
                        thisattr["fillColor"] = getFaceColor(face)
                        thisattr["depth"] = currentDepth
                        parts = self.addClippedPoly(contourPoly(
                            face.contour()),
                                                    container=compound,
                                                    **thisattr)

                        if returnFaces:
                            result.extend([(face, part) for part in parts])

                for anchor in face.holeContours():
                    todo.extend(maputils.holeComponent(anchor))

            currentDepth -= 1

        return result
示例#8
0
def addMapOverlay(fe, overlay, skipBorder=False, **attr):
    qtColor2figColor = figexport.qtColor2figColor

    # FIXME: str(type(overlay)).contains(...) instead?
    if isinstance(overlay, ROISelector):
        color = qtColor2figColor(overlay.color, fe.f)
        return fe.addROIRect(overlay.roi, penColor=color, **attr)
    elif isinstance(overlay, (MapNodes, MapEdges, MapFaces)):
        oldScale, oldOffset, oldROI = fe.scale, fe.offset, fe.roi

        if isinstance(overlay, MapFaces):
            zoom = overlay.edgeOverlay._zoom
        else:
            zoom = overlay._zoom
        extraZoom = float(zoom) / overlay.viewer.zoomFactor()
        fe.scale *= extraZoom
        fe.roi = BoundingBox(fe.roi.begin() / extraZoom,
                             fe.roi.end() / extraZoom)
        map = overlay._map()

        if isinstance(overlay, MapNodes):
            radius = overlay.origRadius
            if not overlay.relativeRadius:
                radius /= float(overlay._zoom)
            color = qtColor2figColor(overlay.color, fe.f)

            result = fe.addMapNodes(map,
                                    radius,
                                    fillColor=color,
                                    lineWidth=0,
                                    **attr)
        elif isinstance(overlay, MapEdges):
            attr = dict(attr)
            if overlay.width:
                attr["lineWidth"] = overlay.width

            if overlay.colors:
                result = fig.Compound(fe.f)
                for edge in map.edgeIter():
                    edgeColor = overlay.colors[edge.label()]
                    if edgeColor:
                        fe.addClippedPoly(edge,
                                          penColor=qtColor2figColor(
                                              edgeColor, fe.f),
                                          container=result,
                                          **attr)
            elif overlay.color:
                result = fe.addMapEdges(map,
                                        skipBorder=skipBorder,
                                        penColor=qtColor2figColor(
                                            overlay.color, fe.f),
                                        **attr)
            else:
                result = fig.Compound(fe.f)

            if overlay.protectedColor:
                attr["penColor"] = \
                    qtColor2figColor(overlay.protectedColor, fe.f)
                attr["lineWidth"] = overlay.protectedWidth or overlay.width
                it = skipBorder and maputils.nonBorderEdges(map) \
                     or map.edgeIter()
                for edge in it:
                    if edge.flag(flag_constants.ALL_PROTECTION):
                        fe.addClippedPoly(edge, container=result, **attr)
        else:  # isinstance(overlay, MapFaces)
            attr = dict(attr)
            if overlay.color:
                if overlay.width:
                    attr["lineWidth"] = overlay.width
                attr["penColor"] = qtColor2figColor(overlay.color, fe.f)
            if overlay.fillColor:
                attr["fillColor"] = qtColor2figColor(overlay.fillColor, fe.f)
                attr["fillStyle"] = fig.FillStyle.Solid
            result = fig.Compound(fe.f)
            for face in map.faceIter():
                if face.flag(overlay.flags):
                    if face.holeCount:
                        assert not overlay.fillColor or not overlay.color, "FIXME: cannot currently export filled+stroked polygons with holes"
                    if not overlay.color:
                        wholePoly = list(contourPoly(face.contour()))
                        back = wholePoly[0]
                        assert wholePoly[-1] == back
                        for dart in face.holeContours():
                            wholePoly.extend(contourPoly(dart))
                            wholePoly.append(back)
                        fe.addClippedPoly(wholePoly, container=result, **attr)
                    else:
                        for dart in face.contours():
                            fe.addClippedPoly(contourPoly(dart),
                                              container=result,
                                              **attr)

        fe.scale, fe.offset, fe.roi = oldScale, oldOffset, oldROI
        return result
    else:
        return figexport.addStandardOverlay(fe, overlay, **attr)