예제 #1
0
def get_svg_html(mpl_figures):
    svg_images = []
    with make_tmp_folder() as tmp_dir:
        for fig in mpl_figures:
            tmp_svg = "%s/mplfig.svg" % (tmp_dir)
            fig.savefig(tmp_svg)
            fig_data = open(tmp_svg, "rb").readlines()
            svg_images.append(fig_data)
    return svg_images
예제 #2
0
def get_svg_html(mpl_figures):
  svg_images = []
  with make_tmp_folder() as tmp_dir:  
    for fig in mpl_figures:
      tmp_svg = "%s/mplfig.svg" %(tmp_dir)
      fig.savefig(tmp_svg)
      fig_data = open(tmp_svg,"rb").readlines()
      svg_images.append(fig_data)
  return svg_images
예제 #3
0
 def get_static_svg(self):
     '''Generate static svg of atlas (cannot manipulate in d3)'''
     svg_data = []
     with make_tmp_folder() as temp_dir:
         output_file='%s/atlas.svg' %(temp_dir)
         plotting.plot_roi(self.mr,annotate=False,draw_cross=False,cmap="nipy_spectral",black_bg=False, output_file=output_file)
         svg_file = open(output_file,'r')
         svg_data = svg_file.readlines()
         svg_file.close()
     return svg_data[4:]
예제 #4
0
 def get_static_svg(self):
     '''Generate static svg of atlas (cannot manipulate in d3)'''
     svg_data = []
     with make_tmp_folder() as temp_dir:
         output_file='%s/atlas.svg' %(temp_dir)
         plotting.plot_roi(self.mr,annotate=False,draw_cross=False,cmap="nipy_spectral",black_bg=False, output_file=output_file)
         svg_file = open(output_file,'r')
         svg_data = svg_file.readlines()
         svg_file.close()
     return svg_data[4:]
예제 #5
0
def view(html_snippet):
    with make_tmp_folder() as tmp_dir:
        # Write to temporary file
        tmp_file = "%s/pycompare.html" % (tmp_dir)
        internal_view(html_snippet, tmp_file)
예제 #6
0
    def make_svg(self,views):
        '''Generate path-based svg of atlas (paths we can manipulate in d3)'''
        import cairo
         # We will save complete svg (for file), partial (for embedding), and paths
        svg_data = dict(); svg_data_partial = dict(); svg_data_file = dict();
        if isinstance(views,str):
            views = [views]
        views = [v.lower() for v in views]
        self.views = views
        mr = self.mr.get_data()
        middles = [numpy.round(x/2) for x in self.mr.get_shape()]

        # Create a color lookup table
        colors_html = get_colors(len(self.labels),"hex")
        self.color_lookup = self.make_color_lookup(colors_html)

        with make_tmp_folder() as temp_dir:

            # Get all unique regions (may not be present in every slice)
            regions = [ x for x in numpy.unique(mr) if x != 0]

            # Get colors - will later be changed
            colors = get_colors(len(self.labels),"decimal")

            # Generate an axial, sagittal, coronal view
            slices = dict()
            for v in views:
                # Keep a list of region names that correspond to paths
                region_names = []

                # Generate each of the views
                if v == "axial": slices[v] = numpy.rot90(mr[:,:,middles[0]],2)
                elif v == "sagittal" : slices[v] = numpy.rot90(mr[middles[1],:,:],2)
                elif v == "coronal" : slices[v] = numpy.rot90(mr[:,middles[2],:],2)

                # For each region in the view, but not 0
                regions = [ x for x in numpy.unique(slices[v]) if x != 0]

                # Write svg to temporary file
                output_file = '%s/%s_atlas.svg' %(temp_dir,v)
                fo = file(output_file, 'wb')

                # Set up the "context" - what cairo calls a canvas
                width, height  = numpy.shape(slices[v])
                surface = cairo.SVGSurface (fo, width*3, height*3)
                ctx = cairo.Context (surface)
                ctx.scale(3.,3.)

                # 90 degree rotation matrix
                rotation_matrix = cairo.Matrix.init_rotate(numpy.pi/2)

                for rr in range(0,len(regions)):
                    index_value = regions[rr]
                    #region_name = self.labels[str(index_value)].label
                    filtered = numpy.zeros(numpy.shape(slices[v]))
                    filtered[slices[v] == regions[rr]] = 1
                    region = img_as_float(find_boundaries(filtered)) # We aren't using Canny anymore...

                    ctx.set_source_rgb (float(colors[index_value-1][0]), float(colors[index_value-1][1]), float(colors[index_value-1][2])) # Solid color

                    # Segment!
                    segments_fz = felzenszwalb(region, scale=100, sigma=0.1, min_size=10)

                    # For each cluster in the region, skipping value of 0
                    for c in range(1,len(numpy.unique(segments_fz))):
                        cluster = numpy.zeros(numpy.shape(region))
                        cluster[segments_fz==c] = 1
                        # Create distance matrix for points
                        x,y = numpy.where(cluster==1)
                        points = [[x[i],y[i]] for i in range(0,len(x))]
                        disty = squareform(pdist(points, 'euclidean'))
                        # This keeps track of which we have already visited
                        visited = []; row = 0; current = points[row]
                        visited.append(row)

                        # We need to remember the first point, for the last one
                        fp = current

                        while len(visited) != len(points):
                            thisx = current[0]
                            thisy = current[1]
                            ctx.move_to(thisx, thisy)
                            # Find closest point, only include columns we have not visited
                            distances = disty[row,:]
                            distance_lookup = dict()
                            # We need to preserve indices but still eliminate visited
                            for j in range(0,len(distances)):
                                if j not in visited: distance_lookup[j] = distances[j]
                            # Get key minimum distance
                            row = min(distance_lookup, key=distance_lookup.get)
                            next = points[row]
                            nextx = next[0]
                            nexty = next[1]
                            # If the distance is more than N pixels, close the path
                            # This resolves some of the rough edges too
                            if min(distance_lookup) > 70:
                                ctx.line_to(fp[0],fp[1])
                                #cp = [(current[0]+fp[0])/2,(current[1]+fp[1])/2]
                                #ctx.curve_to(fp[0],fp[1],cp[0],cp[1],cp[0],cp[1])
                                ctx.set_line_width(1)
                                ctx.close_path()
                                fp = next
                            else:
                                #cp = [(current[0]+nextx)/2,(current[1]+nexty)/2]
                                #ctx.curve_to(nextx,nexty,cp[0],cp[1],cp[0],cp[1])
                                ctx.line_to(nextx, nexty)
                                # Set next point to be current
                            visited.append(row)
                            current = next

                        # Go back to the first point
                        ctx.move_to(current[0],current[1])
                        #cp = [(current[0]+fp[0])/2,(current[1]+fp[1])/2]
                        #ctx.curve_to(fp[0],fp[1],cp[0],cp[1],cp[0],cp[1])
                        ctx.line_to(fp[0],fp[1])
                        # Close the path
                        ctx.set_line_width (1)
                        ctx.stroke()

                # Finish the surface
                surface.finish()
                fo.close()

                # Now grab the file, set attributes
                # Give group name based on atlas, region id based on matching color
                dom = minidom.parse(output_file)
                for group in dom.getElementsByTagName("g"):
                    group.setAttribute("id",os.path.split(self.file)[-1])
                    group.setAttribute("class",v)
                expression = re.compile("stroke:rgb")
                # Add class to svg - important so can manipulate in d3
                dom.getElementsByTagName("svg")[0].setAttribute("class",v)
                for path in dom.getElementsByTagName("path"):
                    style = path.getAttribute("style")
                    # This is lame - but we have to use the color to look up the region
                    color = [x for x in style.split(";") if expression.search(x)][0]
                    color = [percent_to_float(x) for x in color.replace("stroke:rgb(","").replace(")","").split(",")]
                    region_index = [x for x in range(0,len(colors)) if numpy.equal(colors[x],color).all()][0]+1
                    region_label = self.labels[str(region_index)].label
                    # We don't want to rely on cairo to style the paths
                    self.remove_attributes(path,"style")
                    self.set_attributes(path,["id","stroke"],[region_label,self.color_lookup[region_label]])
                svg_data_file[v] = dom.toxml()
                svg_data[v] = dom.toxml().replace("<?xml version=\"1.0\" ?>","") # get rid of just xml tag
                svg_data_partial[v] = "/n".join(dom.toxml().split("\n")[1:-1])

        return svg_data, svg_data_partial, svg_data_file
예제 #7
0
def view(html_snippet):
  with make_tmp_folder() as tmp_dir:  
    # Write to temporary file
    tmp_file = "%s/pycompare.html" %(tmp_dir)
    internal_view(html_snippet,tmp_file)
예제 #8
0
    def make_svg(self, views):
        '''Generate path-based svg of atlas (paths we can manipulate in d3)'''

        import cairo
        # We will save complete svg for file, partial for embedding, and paths
        svg_data = dict()
        svg_data_partial = dict()
        svg_data_file = dict()

        if isinstance(views, str):
            views = [views]
        self.views = [v.lower() for v in views]
        mr = self.mr.get_data()
        middles = [numpy.round(old_div(x, 2)) for x in self.mr.get_shape()]

        # Create a color lookup table
        colors_html = get_colors(len(self.labels), "hex")
        self.color_lookup = self.make_color_lookup(colors_html)

        with make_tmp_folder() as temp_dir:

            # Get all unique regions (may not be present in every slice)
            regions = [x for x in numpy.unique(mr) if x != 0]

            # Get colors - will later be changed
            colors = get_colors(len(self.labels), "decimal")

            # Generate an axial, sagittal, coronal view
            slices = dict()
            for v in views:
                # Keep a list of region names that correspond to paths
                region_names = []

                # Generate each of the views
                if v == "axial":
                    slices[v] = numpy.rot90(mr[:, :, middles[0]], 2)
                elif v == "sagittal":
                    slices[v] = numpy.rot90(mr[middles[1], :, :], 2)
                elif v == "coronal":
                    slices[v] = numpy.rot90(mr[:, middles[2], :], 2)

                # For each region in the view, but not 0
                regions = [x for x in numpy.unique(slices[v]) if x != 0]

                # Write svg to temporary file
                output_file = '%s/%s_atlas.svg' % (temp_dir, v)
                fo = file(output_file, 'wb')

                # Set up the "context" - what cairo calls a canvas
                width, height = numpy.shape(slices[v])
                surface = cairo.SVGSurface(fo, width * 3, height * 3)
                ctx = cairo.Context(surface)
                ctx.scale(3., 3.)

                # 90 degree rotation matrix
                rotation_matrix = cairo.Matrix.init_rotate(old_div(
                    numpy.pi, 2))

                for rr in range(0, len(regions)):
                    index_value = regions[rr]

                    #region_name = self.labels[str(index_value)].label
                    filtered = numpy.zeros(numpy.shape(slices[v]))
                    filtered[slices[v] == regions[rr]] = 1
                    # We aren't using Canny anymore...
                    region = img_as_float(find_boundaries(filtered))

                    # Solid color
                    ctx.set_source_rgb(float(colors[index_value - 1][0]),
                                       float(colors[index_value - 1][1]),
                                       float(colors[index_value - 1][2]))

                    # Segment!
                    segments_fz = felzenszwalb(region,
                                               scale=100,
                                               sigma=0.1,
                                               min_size=10)

                    # For each cluster in the region, skipping value of 0
                    for c in range(1, len(numpy.unique(segments_fz))):
                        cluster = numpy.zeros(numpy.shape(region))
                        cluster[segments_fz == c] = 1

                        # Create distance matrix for points
                        x, y = numpy.where(cluster == 1)
                        points = [[x[i], y[i]] for i in range(0, len(x))]
                        disty = squareform(pdist(points, 'euclidean'))

                        # This keeps track of which we have already visited
                        visited = []
                        row = 0
                        current = points[row]
                        visited.append(row)

                        # We need to remember the first point, for the last one
                        fp = current

                        while len(visited) != len(points):
                            thisx = current[0]
                            thisy = current[1]
                            ctx.move_to(thisx, thisy)

                            # Find closest point, only include cols not visited
                            distances = disty[row, :]
                            distance_lookup = dict()

                            # preserve indices but still eliminate visited
                            for j in range(0, len(distances)):
                                if j not in visited:
                                    distance_lookup[j] = distances[j]

                            # Get key minimum distance
                            row = min(distance_lookup, key=distance_lookup.get)
                            next = points[row]
                            nextx = next[0]
                            nexty = next[1]

                            # If the distance is more than N pixels, close path
                            # This resolves some of the rough edges too
                            if min(distance_lookup) > 70:
                                ctx.line_to(fp[0], fp[1])
                                ctx.set_line_width(1)
                                ctx.close_path()
                                fp = next
                            else:
                                ctx.line_to(nextx, nexty)

                            # Set next point to be current
                            visited.append(row)
                            current = next

                        # Go back to the first point
                        ctx.move_to(current[0], current[1])
                        ctx.line_to(fp[0], fp[1])

                        # Close the path
                        ctx.set_line_width(1)
                        ctx.stroke()

                # Finish the surface
                surface.finish()
                fo.close()

                # Now grab the file, set attributes
                # group name based on atlas, region id based on matching color
                dom = minidom.parse(output_file)
                for group in dom.getElementsByTagName("g"):
                    group.setAttribute("id", os.path.split(self.file)[-1])
                    group.setAttribute("class", v)
                regexp = re.compile("stroke:rgb")

                # Add class to svg - important so can manipulate in d3
                dom.getElementsByTagName("svg")[0].setAttribute("class", v)

                for path in dom.getElementsByTagName("path"):
                    style = path.getAttribute("style")

                    # we have to use the color to look up the region
                    color = [x for x in style.split(";")
                             if regexp.search(x)][0]
                    color = [
                        percent_to_float(x) for x in color.replace(
                            "stroke:rgb(", "").replace(")", "").split(",")
                    ]
                    region_index = [
                        x for x in range(0, len(colors))
                        if numpy.equal(colors[x], color).all()
                    ][0] + 1
                    region_label = self.labels[str(region_index)].label

                    # We don't want to rely on cairo to style the paths
                    self.remove_attributes(path, "style")
                    self.set_attributes(
                        path, ["id", "stroke"],
                        [region_label, self.color_lookup[region_label]])

                svg_data_file[v] = dom.toxml()

                # get rid of just xml tag
                svg_data[v] = dom.toxml().replace("<?xml version=\"1.0\" ?>",
                                                  "")
                svg_data_partial[v] = "/n".join(dom.toxml().split("\n")[1:-1])

        return svg_data, svg_data_partial, svg_data_file