Esempio n. 1
0
def simplemain():
    """A simple main"""
    from nkpylib.nkutils import specializeDict, str2kvdict
    if len(sys.argv) < 6:
        print 'Usage: python %s <aligner name> <input image name> <output image name> <fiducials> <outparams>' % (sys.argv[0])
        sys.exit()
    name, infname, outfname, fiducials, outparams = sys.argv[1:6]
    a = Aligner(name=name)
    im = Image.open(infname)
    fiducials = parseFiducials(fiducials)
    outparams = str2kvdict(outparams, sep='@', dlm='::')
    print 'INFILE:', infname
    print 'FIDUCIALS:', fiducials
    print 'OUTPARAMS:', outparams
    aligned, params = a.align(im, fiducials=fiducials, outparams=outparams)
    print 'PARAMS:', params
    saveImage(aligned, outfname, params)
    print 'OUTFILE:', outfname
    sys.exit()
Esempio n. 2
0
def parseFiducials(s):
    """Parses a fiducials dictionary from the given string"""
    from nkpylib.nkutils import specializeDict, str2kvdict
    # make the type-specialized dict
    fids = specializeDict(str2kvdict(s, sep='@', dlm='::'))
    # convert _x and _y fids to pairs
    names = set(f.rsplit('_', 1)[0] for f in fids if f.lower().endswith('_x') or f.lower().endswith('_y'))
    def popic(name, c):
        """Pops the fids with given name and ending char, ignoring case"""
        try:
            #return fids.pop(name+'_'+c.lower())
            return fids[name+'_'+c.lower()]
        except KeyError:
            #return fids.pop(name+'_'+c.upper())
            return fids[name+'_'+c.upper()]

    for n in names:
        fids[n] = x, y = popic(n, 'x'), popic(n, 'y')
    return fids
Esempio n. 3
0
def processLine(line):
    """Process a single line of input, returning a single line of output as a string.
    Input on stdin is
        <input path>\t<output fmt>\t<aligner>\t<fiducials>\t<output parameters>
    where:
      - <input path> is a local path of the input image to align (not a url),
      - <output fmt> is a format string which will generate the output path. It's given a dict with:
              dfij:  doifj
              blah: difj
      - <aligner> is the name of the aligner to use,
      - <fiducials> is a list of 'key@value' pairs, joined using ::
          These are used for determining feature locations, which the aligners are defined relative to.
          Any extra fiducials (not needed by the given aligner) are ignored.
          If there is a missing fiducial, an error is returned.
      - <output parameters> is an optional list of 'key@value' pairs, joined using '::'
          These are used for defining parameters about the output. Currently, we support:
                 crop: 'x0,y0,x1,y1' rect from which to extract features from. This is
                       first cut from the image and provides the extents relative to which
                       the feature locations are assumed to be located.
                       [default: no crop]

                width: the width to scale the cropped input to (aspect ratio NOT preserved)
                       [default: original resolution]

               height: the height to scale the cropped input to (aspect ratio NOT preserved)
                       [default: original resolution]

             drawfids: how to draw fiducials on output. options:
                           none: don't draw fiducials [default]
                           circle: draw a circle
                           rectangle: draw a rectangle

         drawfidsline: the color to draw fiducial outlines in, as any valid color string (only if drawfids is on)
                       [default: green]

         drawfidsfill: the color to fill drawn fiducials in, as any valid color string (only if drawfids is on)
                       [default: green]

            drawfidsr: the radius of the circle to draw fiducials in
                       [default: 3]

               outfmt: the output format to print on stdout. This is a standard python format string,
                       to which we'll pass a dictionary with the following fields:
                           basename: input file basename
                           inpath: input file path
                           outpath: output file path
                           outfmt: the passed-in output file format string
                           aligner: the passed-in aligner string
                           fiducials: the passed-in input parameters string
                           outparams: the passed-in output parameters string
                       [default: '%(inpath)s\t%(outpath)s']

               errfmt: what to print in case of error, again as a python format string.
                       The fmtdict is like in 'fmt', and also containing:
                           errortype: a python exception type name
                           errormsg: the error message
                       [default: 'error']

    A full input string might look like:
        FIXME
    """
    #TODO test out various outfmt options
    #TODO how to specify if we want to write EXIF or not?
    from collections import defaultdict
    fmtdict = defaultdict(str)
    DEFAULT_OUTPARAMS = defaultdict(str)
    DEFAULT_OUTPARAMS['outfmt'] = DEFAULT_OUTPUT_FMT
    DEFAULT_OUTPARAMS['errfmt'] = DEFAULT_ERROR_FMT
    DEFAULT_OUTPARAMS['drawfids'] = 'none'
    DEFAULT_OUTPARAMS['drawfidsline'] = 'green'
    DEFAULT_OUTPARAMS['drawfidsfill'] = 'green'
    DEFAULT_OUTPARAMS['drawfidsr'] = 3

    # parse elements
    els = line.split('\t')
    try:
        # input and output
        fmtdict['inpath'] = inpath = els.pop(0)
        fmtdict['basename'] = basename = os.path.basename(inpath)
        fmtdict['outpathfmt'] = outpathfmt = els.pop(0)
        #print path, basename, fmtdict, outfmt
        # aligner
        fmtdict['aligner'] = aligner = els.pop(0)
        #print aligner
        # fiducials
        fmtdict['fiducials'] = fiducials = els.pop(0)
        fiducials = parseFiducials(fiducials)
        # output params
        outparams = dict(**DEFAULT_OUTPARAMS)
        #print outparams
        if els:
            # output params are optional, so we don't want to raise an exception here
            fmtdict['outparams'] = els.pop(0)
            #print fmtdict['outparams']
            outparams.update(str2kvdict(fmtdict['outparams'], sep='@', dlm='::'))
            #print outparams

        # at this stage, we have everything we need
        # first make sure the file exists and open it
        if not os.path.exists(inpath): raise IOError('Image does not exist')
        im = Image.open(inpath)
        # process the image
        a = Aligner(name=aligner)
        aligned, params = a.align(im, fiducials=fiducials, outparams=outparams)
        fmtdict.update(params)
        outparams['outfmt'] = outparams['outfmt'].replace(r'\t', '\t').replace(r'\n', '\n')
        # save the output image
        fmtdict['outpath'] = outpath = outpathfmt % fmtdict
        #print outpathfmt, inpath, basename, fmtdict, outpath
        fmtdict['outpathfmt'] = fmtdict['outpathfmt'].replace(r'\t', '\t').replace(r'\n', '\n')
        saveImage(aligned, outpath, params)
        # generate the output string
        ret = outparams['outfmt'] % (fmtdict)
        return ret
    except Exception, e:
        raise
        # add the error values to the fmtdict
        fmtdict['errortype'] = type(e).__name__
        try:
            fmtdict['errormsg'] = e
        except Exception:
            pass
        # generate and return the error string
        errstr = outparams['errfmt'] % fmtdict
        return errstr