def profile_main(): DEFAULT_CACHE = ".radialx/cache" header() parser = doopts() (options, args) = parser.parse_args() try: config_file = args[0] except IndexError: usage(parser, 'No config file specified.') tk = TK.Tk() tk.title('profilex') tk.protocol("WM_DELETE_WINDOW", sys.exit) plot_f = TK.Frame(tk, relief=TK.RIDGE, border=2) plot_f.pack(side=TK.TOP, fill=TK.BOTH, expand=TK.YES) qb = TK.Button(tk, fg="#aa0000", text="Quit", cursor="hand2", command=sys.exit) qb.pack() task_pane = TK.Frame(tk) task_pane.pack(expand=TK.NO, fill=TK.X) statusvar = TK.StringVar() status = TK.Label(task_pane, textvariable=statusvar, justify=TK.LEFT) status.pack(expand=TK.NO, fill=TK.BOTH, side=TK.LEFT) pb_f = TK.Frame(tk, relief=TK.RIDGE, border=2) pb_f.pack(side=TK.TOP, fill=TK.BOTH, expand=TK.NO) task_svar = TK.StringVar() TK.Label(tk, width=70, textvariable=task_svar).pack(side=TK.TOP) task_pb = PB(tk, svar=task_svar, height=8) task_pb.pack(side=TK.TOP, expand=TK.NO, fill=TK.BOTH) job_svar = TK.StringVar() TK.Label(tk, width=70, textvariable=job_svar).pack(side=TK.TOP) job_pb = PB(tk, job_svar, height=8) job_pb.pack(side=TK.TOP, expand=TK.NO, fill=TK.BOTH) # TK.Button(tk, text='Quit', command=tk.destroy).pack(side=TK.TOP) tk.update_idletasks() cfg = _radialx.load_config(config_file) general = cfg['general'] spectradb = _radialx.load_config(general['spec_db']) # interpolate fields for spectra (e.g. %latest%) spec_dir = general['spec_dir'] suffix = ("yml", "yaml", "spec", "json") field = "%latest%" latest = None for key, spec in spectradb.items(): if spec['filename'] == field: if latest is None: latest = last_made(dirpath=spec_dir, suffix=suffix) spec['filename'] = latest imagesdb = _radialx.load_config(general['img_db']) if general['cache'] is None: cache = DEFAULT_CACHE else: cache = general['cache'] cache = pyfscache.FSCache(cache) if general['mode'] == "averaging": config = cfg['averaging'] groups_img = _radialx.load_config(general['img_groups']) groups_img = groups_img['images'] groups_spec = _radialx.load_config(general['spec_groups']) groups_spec = groups_spec['spectra'] cfg['groups'] = {'images' : groups_img, 'spectra' : groups_spec} spectra = _radialx.get_spectra(cfg, spectradb, "averaging") images = _radialx.get_images(cfg, imagesdb, "averaging") pltcfg = _radialx.load_config(config['plot_config']) plt = MyXYPlot(master=plot_f, figsize=pltcfg['plot_size'], dpi=pltcfg['dpi']) sp = _radialx.load_spectra(config, spectra) sp_values = sp.values() ms = _radialx.averages(config, images, pltcfg=pltcfg, plt=plt, job=job_pb.update, task=task_pb.update, cache=cache) ms_values = ms.values() TCs = sp_values + ms_values _radialx.sharpnesses(config, TCs) # if ((config['scaled_to'] is not None) and # (len(images) + len(spectra) == 2)): if config['scaled_to'] is not None: if len(images) + len(spectra) == 2: db = SQLite.Database(general['score_db']) title = "Model Name" table = db.create("scores", # pdb model that produced spectrum ("model", TEXT), # key from image database ("image_key", TEXT), # Ro score for the scaling ("score", REAL), # R**2 statistic ("Rsq", REAL), # fitted alpha scaling parameter ("alpha", REAL), # fitted m scaling parameter ("m", REAL), # fitted b scaling parameter ("b", REAL), # fitted B scaling parameter ("Bfac", REAL), # json of the image entry from the images db ("image", TEXT), # base64 of bz2 of model pdb file ("pdb", TEXT), # base64 of numpy serialized spectrum array # in [ 2-theta, intensity ] pairs ("spectrum", TEXT), # json of the profilex averaging config section ("config", TEXT), # json of the profilex general config section ("general", TEXT), mode="open") if options.model is not None: if os.path.exists(options.model): options.model = None elif table(model=options.model): options.model = None title = "Unique Model Name" latest_pdb = last_made(dirpath=general['model_dir'], suffix=".pdb") while options.model is None: options.model = askopenfilename( title=title, parent=tk, filetypes=[("PDB", "*.pdb")], initialdir=general['model_dir'], initialfile=latest_pdb) if not options.model: msg = "Must proceed with a\nunique model name.\n\nContinue?" if askyesno("Continue", msg, parent=tk): options.model = None else: sys.exit() else: rows = table(model=options.model) if rows: bn = os.path.basename(options.model) tplt = ("Model name '%s'\nis not unique.\n\n" + "Overwrite score?") msg = tplt % bn overwrite = askyesnocancel("Overwrite Score", msg) if overwrite is None: options.model = None elif overwrite: if len(rows) > 1: msg = ("%s Records with model\nnamed '%s'.\n\n" + "Erase all?") % (len(rows), bn) if askyesno("Erase Records", msg, parent=tk): for row in rows: del table[row['__id__']] else: config['save_score'] = False else: config['save_score'] = False else: table = None options.model = None config['pdb_model'] = options.model T = None Cs = [] for TC in TCs: if TC['image_key'] == config['scaled_to']: T = TC else: Cs.append(TC) std_outlet = StdOutlet(tk) if T is None: tplt = "Unrecognized value for scaled_to: %s" msg = tplt % config['scaled_to'] raise _radialx.ConfigError(msg) _radialx.scale_several(config, Cs, T, general, std_outlet, table) msc = ms.copy() msc.update(sp) spmsc = msc.reversed() nimgs = _radialx.plot_images(plt, spmsc, config, pltcfg, 0) statusvar.set("%s Images Processed and Plotted" % nimgs) task_pb.deactivate() job_pb.deactivate() elif general['mode'] == "difference": config = cfg['difference'] if config['scaling_target'] in ("NONE", "None", "none", None): config['scaling_target'] = None config['images'] = [config['negative'], config['positive']] # adapting difference config to averaging config # maybe just change the settings file format? config['scaled_to'] = config['negative'] config['roi'] = config['limits'] config['roi_bins'] = config['bins'] config['img_bins'] = config['bins'] config['norm_type'] = None config['stretch'] = False config['do_norm'] = False config['smooth_spectra'] = False images = _radialx.get_images(cfg, imagesdb, "difference") keys = [k for (k, d) in images] pltcfg = _radialx.load_config(config['plot_config']) plt = MyXYPlot(master=plot_f, figsize=pltcfg['plot_size'], dpi=pltcfg['dpi']) plt2 = MyXYPlot(master=plot_f, figsize=pltcfg['plot_size'], dpi=pltcfg['dpi'], sibling=plt) # _radialx.plot_spectra(config, spectra, pltcfg, plt, cache=cache) ms = _radialx.averages(config, images, pltcfg=pltcfg, plt=plt, job=job_pb.update, task=task_pb.update, cache=cache) TCs = ms.values() if TCs[0]['image_key'] == config['scaled_to']: T = TCs[0] C = TCs[1] else: T = TCs[1] C = TCs[0] if config['scaling_target'] is None: T['scaled'] = T['sum Is'] C['scaled'] = C['sum Is'] _radialx.bin_equivalent(T) _radialx.bin_equivalent(C) else: Cs = [C] std_outlet = StdOutlet(tk) table = None _radialx.scale_several(config, Cs, T, general, std_outlet, table) msc = ms.copy() nimgs = _radialx.plot_images(plt, msc, config, pltcfg, 0) statusvar.set("%s Images Processed and Plotted" % nimgs) twoths = T['bin middles two-theta'] avis = C['scaled'] - T['scaled'] if avis.min() < 0: avis = avis - avis.min() spectrum_file = config['output'] + ".yml" _radialx.write_spectrum(spectrum_file, config['output'], twoths, avis, False) # manually build a spec record for load_spectra() twoths_degs = T['bin middles two-theta degs'] record = OrderedDict() record["filename"] = spectrum_file for k in ["descr", "nickname", "wavelength"]: record[k] = config[k] record['__filepath__'] = spectrum_file pattern = numpy.array([twoths_degs, avis]).T record['__data__'] = OrderedDict() record['__data__']['model'] = config['output'] record['__data__']['pattern'] = pattern spectra = [(config['key'], record)] sp = _radialx.load_spectra(config, spectra) nimgs = _radialx.plot_images(plt, sp, config, pltcfg, 0) task_pb.deactivate() job_pb.deactivate() output = ["\n[%s]" % config['key']] for (k, v) in record.items(): if not k.startswith("__"): try: output.append("%s = %f" % (k, float(v))) except (ValueError, TypeError): output.append("%s = \"%s\"" % (k, v)) output = "\n".join(output) + "\n" std_outlet = StdOutlet(tk) std_outlet(output) elif general['mode'] == "recentering": config = cfg['recentering'] image = imagesdb[config['recenter_image']] plt = MyXYPlot(master=plot_f, figsize=config['plot_size']) # result = {"coords" : coords, # "vals" : vals, # "exes" : exes, # "whys" : whys, # "max_xy" : max_xy} result = _radialx.recenter(general, config, image, plt=plt, job=job_pb.update, task=task_pb.update, cache=cache) # flip x and y for image space # title = "%s\n%s to %s %s (%s px grid)" % params title = "%s : %s" % (image['filename'], result['max_xy']) factor = (config['bin_factor'], config['bin_factor']) # flip exes and whys for image space xy_heat(result['coords'], result['vals'], heat_up=1.0/3.0, xlabs=result['exes'], ylabs=result['whys'], title=title) else: job_pb.update("The mode for the run is not recognized.", 1) tk.mainloop()
def chemfigit(config): program = "chemfigit" cfg = config.copy() # setup logger logger = logging.getLogger(program) log_level = getattr(logging, cfg['log_level'].upper()) logger.setLevel(log_level) ch = logging.StreamHandler() ch.setLevel(log_level) formatter = logging.Formatter("%(name)s [%(levelname)s] %(message)s") ch.setFormatter(formatter) logger.addHandler(ch) # setup paths cfg['cwd'] = os.getcwd() cfg['start_time'] = time.time() cfg['temp_base'] = "%014.2f" % cfg['start_time'] cfg['temp_dir'] = os.path.join(tempfile.gettempdir(), program, cfg['temp_base']) if cfg['tex_file']: cfg['tex_file'] = os.path.abspath(cfg['tex_file']) if cfg['dest_dir'] is None: cfg['dest_dir'] = os.path.dirname(cfg['tex_file']) cfg['abs_dest_dir'] = cfg['dest_dir'] else: cfg['abs_dest_dir'] = os.path.abspath(cfg['dest_dir']) logger.info('Using tex file: %(tex_file)s', cfg) else: if cfg['dest_dir'] is None: curdir = os.path.abspath('.') cfg['tex_file'] = phyles.last_made(curdir, suffix=".tex", depth=cfg['tex_depth']) if cfg['tex_file'] is None: raise ChemFigitError('No tex file found.') cfg['abs_dest_dir'] = os.path.dirname(cfg['tex_file']) else: cfg['abs_dest_dir'] = os.path.abspath(cfg['dest_dir']) cfg['tex_file'] = phyles.last_made(cfg['abs_dest_dir'], suffix=".tex", depth=cfg['tex_depth']) logger.info('Using newest tex file: %(tex_file)s', cfg) cfg['tex_base'] = os.path.basename(cfg['tex_file']) cfg['abs_tex_file'] = os.path.abspath(cfg['tex_file']) cfg['prefix'] = cfg['tex_base'].rsplit(".", 1)[0] cfg['full_pdf_file'] = cfg['prefix'] + ".pdf" # create temp dir if os.path.exists(cfg['temp_dir']): logger.info('Had md5 collision (%s)!', cfg['temp_base']) shutil.rmtree(cfg['temp_dir']) # had md5 collision! logger.info('Making directory: %s', cfg['temp_dir']) os.makedirs(cfg['temp_dir']) # create dest dir if not os.path.exists(cfg['abs_dest_dir']): logger.info('Making directory: %s', cfg['abs_dest_dir']) os.makedirs(cfg['abs_dest_dir']) # insert tex_includes into TEXINPUTS if cfg['tex_includes'] is not None: inputs = cfg['tex_includes'].split(":") inputs = [os.path.abspath(p) for p in inputs] s_inputs = ":".join(inputs) os.environ['TEXINPUTS'] = ":".join([s_inputs, os.environ['TEXINPUTS']]) os.system('echo $TEXINPUTS') # raise SystemExit # do preamble if cfg['preamble'] is not None: found_preamble = False for p in inputs: preamble_path = os.path.join(p, cfg['preamble']) if os.path.exists(preamble_path): cfg['preamble_path'] = preamble_path found_preamble = True break if not found_preamble: tplt = "Could not find preamble '%s'." msg = tplt % (cfg['preamble'],) raise ChemFigitError(msg) with open(preamble_path) as f: preamble_text = f.read() cfg['preamble_base'] = os.path.basename(cfg['preamble']) new_preamble_file = os.path.join(cfg['temp_dir'], cfg['preamble_base']) with open(new_preamble_file, "w") as f: f.write(preamble_text) # copy the tex file logger.info("copying %s to %s", cfg['abs_tex_file'], cfg['temp_dir']) shutil.copy(cfg['abs_tex_file'], cfg['temp_dir']) # change to the temp dir logger.info("Changing dir to %s", cfg['temp_dir']) os.chdir(cfg['temp_dir']) # create the document file cfg['geometry'] = ",".join(["paperwidth=%(paperwidth)s", "paperheight=%(paperheight)s", "margin=%(papermargin)s"]) % cfg doc_setup = r""" \documentclass[letter,%(font_size)spt]{article} \usepackage[%(geometry)s]{geometry} \pagestyle{empty} \input{%(preamble_base)s} \begin{document} \input{%(tex_base)s} \end{document} """ cfg['doc_setup'] = textwrap.dedent(doc_setup)[1:] % cfg cfg['document_prefix'] = cfg['prefix'] + "-document" cfg['tex_document'] = cfg['document_prefix'] + ".tex" with open(cfg['tex_document'], "w") as f: f.write(cfg['doc_setup']) # open log files cfg['out_log_file'] = open("stdout.log", "w") cfg['err_log_file'] = open("stderr.log", "w") # run pdflatex pdflatex_command = "%(pdflatex)s %(tex_document)s" % cfg logger.info('running 1st time: %s', pdflatex_command) subprocess.call(pdflatex_command.split(), stdout=cfg['out_log_file'], stderr=cfg['err_log_file']) logger.info('running 2nd time: %s', pdflatex_command) subprocess.call(pdflatex_command.split(), stdout=cfg['out_log_file'], stderr=cfg['err_log_file']) # crop the pdf cfg['pdf_file'] = "%(prefix)s.pdf" % cfg cfg['document_pdf'] = cfg['document_prefix'] + ".pdf" cfg['cropped_pdf_file'] = "%(prefix)s-crop.pdf" % cfg pdfcrop_command = ("%(pdfcrop)s --margins %(crop_margin)s " + "%(document_pdf)s %(cropped_pdf_file)s") pdfcrop_command = pdfcrop_command % cfg logger.info('running: %s', pdfcrop_command) subprocess.call(pdfcrop_command.split(), stdout=cfg['out_log_file'], stderr=cfg['err_log_file']) # do the outputs for output in cfg['output_formats']: OUTPUTS[output](cfg, logger) # close log files cfg['out_log_file'].close() cfg['err_log_file'].close() # return to cwd os.chdir(cfg['cwd']) return cfg