示例#1
0
def reg_planes_to_img(imgs, path=None, ax=None):
    """Export registered image single planes to a single figure.
    
    Simplified export tool taking a single plane from each registered image
    type, overlaying in a single figure, and exporting to file.
    
    Args:
        imgs (List[:obj:`np.ndarray`]): Sequence of image planes to display.
            The first image is assumed to be greyscale, the second is labels,
            and any subsequent images are borders.
        path (str): Output base path, which will be combined with
            :attr:`config.savefig`; defaults to None to not save.
        ax (:obj:`matplotlib.image.Axes`): Axes on which to plot; defaults
            to False, in which case a new figure and axes will be generated.

    """
    if ax is None:
        # set up new figure with single subplot
        fig, gs = plot_support.setup_fig(
            1, 1, config.plot_labels[config.PlotLabels.SIZE])
        ax = fig.add_subplot(gs[0, 0])
    stacker = StackPlaneIO()
    StackPlaneIO.interp_order = config.transform[
        config.Transforms.INTERPOLATION]
    stacker.images = [img[None] for img in imgs]
    stacker.fn_process = StackPlaneIO.process_plane
    stacker.cmaps_labels = _setup_labels_cmaps(imgs)
    plotted_imgs = stacker.build_stack(ax, scale_bar=False)
    ax_img = plotted_imgs[0][0]
    aspect, origin = plot_support.get_aspect_ratio(config.plane)
    plot_support.fit_frame_to_image(ax_img.figure,
                                    ax_img.get_array().shape, aspect)
    if path:
        plot_support.save_fig(path, config.savefig)
示例#2
0
def plot_clusters_by_label(path, z, suffix=None, show=True, scaling=None):
    """Plot separate sets of clusters for each label.
    
    Args:
        path (str): Base path to blobs file with clusters.
        z (int): z-plane to plot.
        suffix (str): Suffix for ``path``; defaults to None.
        show (bool): True to show; defaults to True.
        scaling (List): Sequence of scaling from blobs' coordinate space
             to that of :attr:`config.labels_img`.

    """
    mod_path = path
    if suffix is not None:
        mod_path = libmag.insert_before_ext(path, suffix)
    blobs = np.load(libmag.combine_paths(mod_path,
                                         config.SUFFIX_BLOB_CLUSTERS))
    label_ids = np.unique(blobs[:, 3])
    fig, gs = plot_support.setup_fig(
        1, 1, config.plot_labels[config.PlotLabels.SIZE])
    ax = fig.add_subplot(gs[0, 0])
    plot_support.hide_axes(ax)

    # plot underlying atlas
    np_io.setup_images(mod_path)
    if config.reg_suffixes[config.RegSuffixes.ATLAS]:
        # use atlas if explicitly set
        img = config.image5d
    else:
        # default to black background
        img = np.zeros_like(config.labels_img)[None]
    stacker = export_stack.setup_stack(img,
                                       mod_path,
                                       slice_vals=(z, z + 1),
                                       labels_imgs=(config.labels_img,
                                                    config.borders_img))
    stacker.build_stack(ax, config.plot_labels[config.PlotLabels.SCALE_BAR])
    # export_stack.reg_planes_to_img(
    #     (np.zeros(config.labels_img.shape[1:], dtype=int),
    #      config.labels_img[z]), ax=ax)

    if scaling is not None:
        print("scaling blobs cluster coordinates by", scaling)
        blobs = blobs.astype(float)
        blobs[:, :3] = np.multiply(blobs[:, :3], scaling)
        blobs[:, 0] = np.floor(blobs[:, 0])

    # plot nuclei by label, colored based on cluster size within each label
    colors = colormaps.discrete_colormap(len(np.unique(blobs[:, 4])),
                                         prioritize_default="cn") / 255.
    col_noise = (1, 1, 1, 1)
    for label_id in label_ids:
        if label_id == 0:
            # skip blobs in background
            continue
        # sort blobs within label by cluster size (descending order),
        # including clusters within all z-planes to keep same order across zs
        blobs_lbl = blobs[blobs[:, 3] == label_id]
        clus_lbls, clus_lbls_counts = np.unique(blobs_lbl[:, 4],
                                                return_counts=True)
        clus_lbls = clus_lbls[np.argsort(clus_lbls_counts)][::-1]
        blobs_lbl = blobs_lbl[blobs_lbl[:, 0] == z]
        for i, (clus_lbl, color) in enumerate(zip(clus_lbls, colors)):
            blobs_clus = blobs_lbl[blobs_lbl[:, 4] == clus_lbl]
            if len(blobs_clus) < 1: continue
            # default to small, translucent dominant cluster points
            size = 0.1
            alpha = 0.5
            if clus_lbl == -1:
                # color all noise points the same and emphasize points
                color = col_noise
                size = 0.5
                alpha = 1
            print(label_id, clus_lbl, color, len(blobs_clus))
            ax.scatter(blobs_clus[:, 2],
                       blobs_clus[:, 1],
                       color=color,
                       s=size,
                       alpha=alpha)
    plot_support.save_fig(mod_path, config.savefig, "_clusplot")
    if show: plot_support.show()
示例#3
0
def stack_to_img(paths,
                 roi_offset,
                 roi_size,
                 series=None,
                 subimg_offset=None,
                 subimg_size=None,
                 animated=False,
                 suffix=None):
    """Build an image file from a stack of images in a directory or an 
    array, exporting as an animated GIF or movie for multiple planes or 
    extracting a single plane to a standard image file format.
    
    Writes the file to the parent directory of path.
    
    Args:
        paths (List[str]): Image paths, which can each be either an image 
            directory or a base path to a single image, including 
            volumetric images.
        roi_offset (Sequence[int]): Tuple of offset given in user order
            ``x,y,z``; defaults to None. Requires ``roi_size`` to not be None.
        roi_size (Sequence[int]): Size of the region of interest in user order 
            ``x,y,z``; defaults to None. Requires ``roi_offset`` to not be None.
        series (int): Image series number; defaults to None.
        subimg_offset (List[int]): Sub-image offset as (z,y,x) to load;
            defaults to None.
        subimg_size (List[int]): Sub-image size as (z,y,x) to load;
            defaults to None.
        animated (bool): True to export as an animated image; defaults to False.
        suffix (str): String to append to output path before extension; 
            defaults to None to ignore.

    """
    # set up figure layout for collages
    size = config.plot_labels[config.PlotLabels.LAYOUT]
    ncols, nrows = size if size else (1, 1)
    num_paths = len(paths)
    collage = num_paths > 1
    figs = {}

    for i in range(nrows):
        for j in range(ncols):
            n = i * ncols + j
            if n >= num_paths: break

            # load an image and set up its image stacker
            path_sub = paths[n]
            axs = []
            # TODO: test directory of images
            # TODO: consider not reloading first image
            np_io.setup_images(path_sub, series, subimg_offset, subimg_size)
            stacker = setup_stack(
                config.image5d,
                path_sub,
                offset=roi_offset,
                roi_size=roi_size,
                slice_vals=config.slice_vals,
                rescale=config.transform[config.Transforms.RESCALE],
                labels_imgs=(config.labels_img, config.borders_img))

            # add sub-plot title unless groups given as empty string
            title = None
            if config.groups:
                title = libmag.get_if_within(config.groups, n)
            elif num_paths > 1:
                title = os.path.basename(path_sub)

            if not stacker.images: continue
            ax = None
            for k in range(len(stacker.images[0])):
                # create or retrieve fig; animation has only 1 fig
                planei = 0 if animated else (stacker.img_slice.start +
                                             k * stacker.img_slice.step)
                fig_dict = figs.get(planei)
                if not fig_dict:
                    # set up new fig
                    fig, gs = plot_support.setup_fig(
                        nrows, ncols,
                        config.plot_labels[config.PlotLabels.SIZE])
                    fig_dict = {"fig": fig, "gs": gs, "imgs": []}
                    figs[planei] = fig_dict
                if ax is None:
                    # generate new axes for the gridspec position
                    ax = fig_dict["fig"].add_subplot(fig_dict["gs"][i, j])
                if title:
                    ax.title.set_text(title)
                axs.append(ax)

            # export planes
            plotted_imgs = stacker.build_stack(
                axs, config.plot_labels[config.PlotLabels.SCALE_BAR],
                size is None or ncols * nrows == 1)

            if animated:
                # store all plotted images in single fig
                fig_dict = figs.get(0)
                if fig_dict:
                    fig_dict["imgs"] = plotted_imgs
            else:
                # store one plotted image per fig; not used currently
                for fig_dict, img in zip(figs.values(), plotted_imgs):
                    fig_dict["imgs"].append(img)

    path_base = paths[0]
    for planei, fig_dict in figs.items():
        if animated:
            # generate animated image (eg animated GIF or movie file)
            animate_imgs(path_base, fig_dict["imgs"], config.delay,
                         config.savefig, suffix)
        else:
            # generate single figure with axis and plane index in filename
            if collage:
                # output filename as a collage of images
                if not os.path.isdir(path_base):
                    path_base = os.path.dirname(path_base)
                path_base = os.path.join(path_base, "collage")

            # insert mod as suffix, then add any additional suffix;
            # can use config.prefix_out for make_out_path prefix
            mod = "_plane_{}{}".format(
                plot_support.get_plane_axis(config.plane), planei)
            out_path = libmag.make_out_path(path_base, suffix=mod)
            if suffix:
                out_path = libmag.insert_before_ext(out_path, suffix)
            plot_support.save_fig(out_path,
                                  config.savefig,
                                  fig=fig_dict["fig"])
示例#4
0
def stack_to_img(paths,
                 roi_offset,
                 roi_size,
                 series=None,
                 subimg_offset=None,
                 subimg_size=None,
                 animated=False,
                 suffix=None):
    """Build an image file from a stack of images in a directory or an 
    array, exporting as an animated GIF or movie for multiple planes or 
    extracting a single plane to a standard image file format.
    
    Writes the file to the parent directory of path.
    
    Args:
        paths (List[str]): Image paths, which can each be either an image 
            directory or a base path to a single image, including 
            volumetric images.
        roi_offset (Sequence[int]): Tuple of offset given in user order
            ``x,y,z``; defaults to None. Requires ``roi_size`` to not be None.
        roi_size (Sequence[int]): Size of the region of interest in user order 
            ``x,y,z``; defaults to None. Requires ``roi_offset`` to not be None.
        series (int): Image series number; defaults to None.
        subimg_offset (List[int]): Sub-image offset as (z,y,x) to load;
            defaults to None.
        subimg_size (List[int]): Sub-image size as (z,y,x) to load;
            defaults to None.
        animated (bool): True to export as an animated image; defaults to False.
        suffix (str): String to append to output path before extension; 
            defaults to None to ignore.

    """
    size = config.plot_labels[config.PlotLabels.LAYOUT]
    ncols, nrows = size if size else (1, 1)
    fig, gs = plot_support.setup_fig(
        nrows, ncols, config.plot_labels[config.PlotLabels.SIZE])
    plotted_imgs = None
    num_paths = len(paths)
    for i in range(nrows):
        for j in range(ncols):
            n = i * ncols + j
            if n >= num_paths: break
            ax = fig.add_subplot(gs[i, j])
            path_sub = paths[n]
            # TODO: test directory of images
            # TODO: avoid reloading first image
            np_io.setup_images(path_sub, series, subimg_offset, subimg_size)
            plotted_imgs = stack_to_ax_imgs(
                ax,
                config.image5d,
                path_sub,
                offset=roi_offset,
                roi_size=roi_size,
                slice_vals=config.slice_vals,
                rescale=config.transform[config.Transforms.RESCALE],
                labels_imgs=(config.labels_img, config.borders_img),
                multiplane=animated,
                fit=(size is None or ncols * nrows == 1))
    path_base = paths[0]
    if animated:
        # generate animated image (eg animated GIF or movie file)
        animate_imgs(path_base, plotted_imgs, config.delay, config.savefig,
                     suffix)
    else:
        # save image as single file
        if roi_offset:
            # get plane index from coordinate at the given axis in ROI offset
            planei = roi_offset[::-1][plot_support.get_plane_axis(
                config.plane, get_index=True)]
        else:
            # get plane index from slice start
            planei = config.slice_vals[0]
        if num_paths > 1:
            # output filename as a collage of images
            if not os.path.isdir(path_base):
                path_base = os.path.dirname(path_base)
            path_base = os.path.join(path_base, "collage")
        mod = "_plane_{}{}".format(plot_support.get_plane_axis(config.plane),
                                   planei)
        if suffix: path_base = libmag.insert_before_ext(path_base, suffix)
        plot_support.save_fig(path_base, config.savefig, mod)