def s_r_save_query(self, *args): names = [''] names.extend(self.query_field_values) try: dex = names.index(self.saved_search_name) except: dex = 0 name = '' while not name: name, ok = QInputDialog.getItem(self, _('Save search/replace'), _('Search/replace name:'), names, dex, True) if not ok: return if not name: error_dialog(self, _("Save search/replace"), _("You must provide a name."), show=True) new = True name = unicode(name) if name in self.queries.keys(): if not question_dialog( self, _("Save search/replace"), _("That saved search/replace already exists and will be overwritten. " "Are you sure?")): return new = False query = {} query['name'] = name query['search_field'] = unicode(self.search_field.currentText()) query['search_mode'] = unicode(self.search_mode.currentText()) query['s_r_template'] = unicode(self.s_r_template.text()) query['s_r_src_ident'] = unicode(self.s_r_src_ident.currentText()) query['search_for'] = unicode(self.search_for.text()) query['case_sensitive'] = self.case_sensitive.isChecked() query['replace_with'] = unicode(self.replace_with.text()) query['replace_func'] = unicode(self.replace_func.currentText()) query['destination_field'] = unicode( self.destination_field.currentText()) query['s_r_dst_ident'] = unicode(self.s_r_dst_ident.text()) query['replace_mode'] = unicode(self.replace_mode.currentText()) query['comma_separated'] = self.comma_separated.isChecked() query['results_count'] = self.results_count.value() query['starting_from'] = self.starting_from.value() query['multiple_separator'] = unicode(self.multiple_separator.text()) self.queries[name] = query self.queries.commit() if new: self.query_field.blockSignals(True) self.query_field.clear() self.query_field.addItem('') self.query_field_values = sorted([q for q in self.queries], key=sort_key) self.query_field.addItems(self.query_field_values) self.query_field.blockSignals(False) self.query_field.setCurrentIndex(self.query_field.findText(name))
def s_r_save_query(self, *args): names = [''] names.extend(self.query_field_values) try: dex = names.index(self.saved_search_name) except: dex = 0 name = '' while not name: name, ok = QInputDialog.getItem(self, _('Save search/replace'), _('Search/replace name:'), names, dex, True) if not ok: return if not name: error_dialog(self, _("Save search/replace"), _("You must provide a name."), show=True) new = True name = unicode(name) if name in self.queries.keys(): if not question_dialog(self, _("Save search/replace"), _("That saved search/replace already exists and will be overwritten. " "Are you sure?")): return new = False query = {} query['name'] = name query['search_field'] = unicode(self.search_field.currentText()) query['search_mode'] = unicode(self.search_mode.currentText()) query['s_r_template'] = unicode(self.s_r_template.text()) query['s_r_src_ident'] = unicode(self.s_r_src_ident.currentText()) query['search_for'] = unicode(self.search_for.text()) query['case_sensitive'] = self.case_sensitive.isChecked() query['replace_with'] = unicode(self.replace_with.text()) query['replace_func'] = unicode(self.replace_func.currentText()) query['destination_field'] = unicode(self.destination_field.currentText()) query['s_r_dst_ident'] = unicode(self.s_r_dst_ident.text()) query['replace_mode'] = unicode(self.replace_mode.currentText()) query['comma_separated'] = self.comma_separated.isChecked() query['results_count'] = self.results_count.value() query['starting_from'] = self.starting_from.value() query['multiple_separator'] = unicode(self.multiple_separator.text()) self.queries[name] = query self.queries.commit() if new: self.query_field.blockSignals(True) self.query_field.clear() self.query_field.addItem('') self.query_field_values = sorted([q for q in self.queries], key=sort_key) self.query_field.addItems(self.query_field_values) self.query_field.blockSignals(False) self.query_field.setCurrentIndex(self.query_field.findText(name))
def computeImage(self, expression=None): """Computes image from expression (if expression is None, pops up dialog)""" if expression is None: (expression, ok) = QInputDialog.getText(self, "Compute image", """Enter an image expression to compute. Any valid numpy expression is supported, and all functions from the numpy module are available (including sub-modules such as fft). Use 'a', 'b', 'c' to refer to images. Examples: "(a+b)/2", "cos(a)+sin(b)", "a-a.mean()", "fft.fft2(a)", etc.""") # (expression,ok) = QInputDialog.getText(self,"Compute image","""<P>Enter an expression to compute. # Use 'a', 'b', etc. to refer to loaded images. Any valid numpy expression is supported, and all the # functions from the numpy module are available. Examples of valid expressions include "(a+b)/2", # "cos(a)+sin(b)", "a-a.mean()", etc. # </P> # """) expression = str(expression) if not ok or not expression: return # try to parse expression arglist = [(chr(ord('a') + ic.getNumber()), ic.image) for ic in self._imagecons] try: exprfunc = eval("lambda " + (",".join([x[0] for x in arglist])) + ":" + expression, numpy.__dict__, {}) except Exception as exc: self.showErrorMessage("""Error parsing expression "%s": %s.""" % (expression, str(exc))) return None # try to evaluate expression self.showMessage("Computing expression \"%s\"" % expression, 10000) busy = BusyIndicator() QApplication.flush() # trim trivial trailing dimensions. This avoids the problem of when an NxMx1 and an NxMx1x1 arrays are added, # the result is promoted to NxMxMx1 following the numpy rules. def trimshape(shape): out = shape while out and out[-1] == 1: out = out[:-1] return out def trimarray(array): return array.reshape(trimshape(array.shape)) try: result = exprfunc(*[trimarray(x[1].data()) for x in arglist]) except Exception as exc: busy = None traceback.print_exc() self.showErrorMessage("""Error evaluating "%s": %s.""" % (expression, str(exc))) return None busy = None if type(result) != numpy.ma.masked_array and type(result) != numpy.ndarray: self.showErrorMessage( """Result of "%s" is of invalid type "%s" (array expected).""" % (expression, type(result).__name__)) return None # convert coomplex results to real if numpy.iscomplexobj(result): self.showErrorMessage("""Result of "%s" is complex. Complex images are currently not fully supported, so we'll implicitly use the absolute value instead.""" % (expression)) expression = "abs(%s)" % expression result = abs(result) # determine which image this expression can be associated with res_shape = trimshape(result.shape) arglist = [x for x in arglist if hasattr(x[1], 'fits_header') and trimshape(x[1].data().shape) == res_shape] if not arglist: self.showErrorMessage("""Result of "%s" has shape %s, which does not match any loaded FITS image.""" % ( expression, "x".join(map(str, result.shape)))) return None # look for an image in the arglist with the same projection, and with a valid dirname # (for the where-to-save hint) template = arglist[0][1] # if all images in arglist have the same projection, then it doesn't matter what we use # else ask if len([x for x in arglist[1:] if x[1].projection == template.projection]) != len(arglist) - 1: options = [x[0] for x in arglist] (which, ok) = QInputDialog.getItem(self, "Compute image", "Coordinate system to use for the result of \"%s\":" % expression, options, 0, False) if not ok: return None try: template = arglist[options.index(which)][1] except: pass # create a FITS image busy = BusyIndicator() dprint(2, "creating FITS image", expression) self.showMessage("""Creating image for %s""" % expression, 3000) QApplication.flush() try: hdu = pyfits.PrimaryHDU(result.transpose(), template.fits_header) skyimage = SkyImage.FITSImagePlotItem(name=expression, filename=None, hdu=hdu) except: busy = None traceback.print_exc() self.showErrorMessage("""Error creating FITS image %s: %s""" % (expression, str(sys.exc_info()[1]))) return None # get directory name for save-to hint dirname = getattr(template, 'filename', None) if not dirname: dirnames = [getattr(img, 'filename') for x, img in arglist if hasattr(img, 'filename')] dirname = dirnames[0] if dirnames else None # create control bar, add to widget stack self._createImageController(skyimage, expression, expression, save=((dirname and os.path.dirname(dirname)) or ".")) self.showMessage("Created new image for %s" % expression, 3000) dprint(2, "image created")
def computeImage(self, expression=None): """Computes image from expression (if expression is None, pops up dialog)""" if expression is None: (expression, ok) = QInputDialog.getText( self, "Compute image", """Enter an image expression to compute. Any valid numpy expression is supported, and all functions from the numpy module are available (including sub-modules such as fft). Use 'a', 'b', 'c' to refer to images. Examples: "(a+b)/2", "cos(a)+sin(b)", "a-a.mean()", "fft.fft2(a)", etc.""" ) # (expression,ok) = QInputDialog.getText(self,"Compute image","""<P>Enter an expression to compute. # Use 'a', 'b', etc. to refer to loaded images. Any valid numpy expression is supported, and all the # functions from the numpy module are available. Examples of valid expressions include "(a+b)/2", # "cos(a)+sin(b)", "a-a.mean()", etc. # </P> # """) expression = str(expression) if not ok or not expression: return # try to parse expression arglist = [(chr(ord('a') + ic.getNumber()), ic.image) for ic in self._imagecons] try: exprfunc = eval( "lambda " + (",".join([x[0] for x in arglist])) + ":" + expression, numpy.__dict__, {}) except Exception as exc: self.showErrorMessage("""Error parsing expression "%s": %s.""" % (expression, str(exc))) return None # try to evaluate expression self.showMessage("Computing expression \"%s\"" % expression, 10000) busy = BusyIndicator() QApplication.flush() # trim trivial trailing dimensions. This avoids the problem of when an NxMx1 and an NxMx1x1 arrays are added, # the result is promoted to NxMxMx1 following the numpy rules. def trimshape(shape): out = shape while out and out[-1] == 1: out = out[:-1] return out def trimarray(array): return array.reshape(trimshape(array.shape)) try: result = exprfunc(*[trimarray(x[1].data()) for x in arglist]) except Exception as exc: busy = None traceback.print_exc() self.showErrorMessage("""Error evaluating "%s": %s.""" % (expression, str(exc))) return None busy = None if type(result) != numpy.ma.masked_array and type( result) != numpy.ndarray: self.showErrorMessage( """Result of "%s" is of invalid type "%s" (array expected).""" % (expression, type(result).__name__)) return None # convert coomplex results to real if numpy.iscomplexobj(result): self.showErrorMessage( """Result of "%s" is complex. Complex images are currently not fully supported, so we'll implicitly use the absolute value instead.""" % (expression)) expression = "abs(%s)" % expression result = abs(result) # determine which image this expression can be associated with res_shape = trimshape(result.shape) arglist = [ x for x in arglist if hasattr(x[1], 'fits_header') and trimshape(x[1].data().shape) == res_shape ] if not arglist: self.showErrorMessage( """Result of "%s" has shape %s, which does not match any loaded FITS image.""" % (expression, "x".join(map(str, result.shape)))) return None # look for an image in the arglist with the same projection, and with a valid dirname # (for the where-to-save hint) template = arglist[0][1] # if all images in arglist have the same projection, then it doesn't matter what we use # else ask if len( [x for x in arglist[1:] if x[1].projection == template.projection ]) != len(arglist) - 1: options = [x[0] for x in arglist] (which, ok) = QInputDialog.getItem( self, "Compute image", "Coordinate system to use for the result of \"%s\":" % expression, options, 0, False) if not ok: return None try: template = arglist[options.index(which)][1] except: pass # create a FITS image busy = BusyIndicator() dprint(2, "creating FITS image", expression) self.showMessage("""Creating image for %s""" % expression, 3000) QApplication.flush() try: hdu = pyfits.PrimaryHDU(result.transpose(), template.fits_header) skyimage = SkyImage.FITSImagePlotItem(name=expression, filename=None, hdu=hdu) except: busy = None traceback.print_exc() self.showErrorMessage("""Error creating FITS image %s: %s""" % (expression, str(sys.exc_info()[1]))) return None # get directory name for save-to hint dirname = getattr(template, 'filename', None) if not dirname: dirnames = [ getattr(img, 'filename') for x, img in arglist if hasattr(img, 'filename') ] dirname = dirnames[0] if dirnames else None # create control bar, add to widget stack self._createImageController( skyimage, expression, expression, save=((dirname and os.path.dirname(dirname)) or ".")) self.showMessage("Created new image for %s" % expression, 3000) dprint(2, "image created")