pyredshift 1.15__tar.gz → 1.17__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {pyredshift-1.15 → pyredshift-1.17}/PKG-INFO +2 -1
- {pyredshift-1.15 → pyredshift-1.17}/README.md +1 -0
- {pyredshift-1.15 → pyredshift-1.17}/pyredshift +36 -4
- {pyredshift-1.15 → pyredshift-1.17}/setup.py +1 -1
- {pyredshift-1.15 → pyredshift-1.17}/src/pyredshift/redshift.py +43 -8
- {pyredshift-1.15 → pyredshift-1.17}/src/pyredshift.egg-info/PKG-INFO +2 -1
- {pyredshift-1.15 → pyredshift-1.17}/LICENSE +0 -0
- {pyredshift-1.15 → pyredshift-1.17}/pyproject.toml +0 -0
- {pyredshift-1.15 → pyredshift-1.17}/setup.cfg +0 -0
- {pyredshift-1.15 → pyredshift-1.17}/src/pyredshift/__init__.py +0 -0
- {pyredshift-1.15 → pyredshift-1.17}/src/pyredshift/pyredshift-help.html +0 -0
- {pyredshift-1.15 → pyredshift-1.17}/src/pyredshift/pyredshift.lines +0 -0
- {pyredshift-1.15 → pyredshift-1.17}/src/pyredshift.egg-info/SOURCES.txt +0 -0
- {pyredshift-1.15 → pyredshift-1.17}/src/pyredshift.egg-info/dependency_links.txt +0 -0
- {pyredshift-1.15 → pyredshift-1.17}/src/pyredshift.egg-info/requires.txt +0 -0
- {pyredshift-1.15 → pyredshift-1.17}/src/pyredshift.egg-info/top_level.txt +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: pyredshift
|
|
3
|
-
Version: 1.
|
|
3
|
+
Version: 1.17
|
|
4
4
|
Summary: Interactive redshifting of 1D astronomical spectra (Python successor of pdlredshift / redshift.f)
|
|
5
5
|
Home-page: https://github.com/karlglazebrook/pyredshift
|
|
6
6
|
Author: Karl Glazebrook
|
|
@@ -70,6 +70,7 @@ Requires python ≥ 3.9 with numpy, matplotlib, astropy and scipy.
|
|
|
70
70
|
|
|
71
71
|
```
|
|
72
72
|
pyredshift spectrum.fits # format auto-detected
|
|
73
|
+
pyredshift https://host/spectrum.fits # straight from an archive URL
|
|
73
74
|
pyredshift spectrum.fits -f sdss # force a format
|
|
74
75
|
pyredshift spectrum.fits -z 2.19 # start from a known redshift
|
|
75
76
|
pyredshift spectrum.fits --retro # retro PGPLOT-style black background
|
|
@@ -36,6 +36,7 @@ Requires python ≥ 3.9 with numpy, matplotlib, astropy and scipy.
|
|
|
36
36
|
|
|
37
37
|
```
|
|
38
38
|
pyredshift spectrum.fits # format auto-detected
|
|
39
|
+
pyredshift https://host/spectrum.fits # straight from an archive URL
|
|
39
40
|
pyredshift spectrum.fits -f sdss # force a format
|
|
40
41
|
pyredshift spectrum.fits -z 2.19 # start from a known redshift
|
|
41
42
|
pyredshift spectrum.fits --retro # retro PGPLOT-style black background
|
|
@@ -199,6 +199,27 @@ def read_outthere(hdul):
|
|
|
199
199
|
return wav, spec
|
|
200
200
|
|
|
201
201
|
|
|
202
|
+
def fetch_url(url):
|
|
203
|
+
"""Download a spectrum URL to a temporary file and return its path.
|
|
204
|
+
The URL's file extension is kept so format auto-detection still works."""
|
|
205
|
+
import shutil
|
|
206
|
+
import tempfile
|
|
207
|
+
import urllib.request
|
|
208
|
+
from urllib.parse import urlparse
|
|
209
|
+
suffix = os.path.splitext(urlparse(url).path)[1] or ".fits"
|
|
210
|
+
print("Downloading %s ..." % url)
|
|
211
|
+
fd, path = tempfile.mkstemp(prefix="pyredshift-", suffix=suffix)
|
|
212
|
+
try:
|
|
213
|
+
with urllib.request.urlopen(url, timeout=120) as resp, \
|
|
214
|
+
os.fdopen(fd, "wb") as out:
|
|
215
|
+
shutil.copyfileobj(resp, out)
|
|
216
|
+
except Exception as e:
|
|
217
|
+
os.unlink(path)
|
|
218
|
+
sys.exit("Could not download %s\n (%s)" % (url, e))
|
|
219
|
+
print(" %d bytes" % os.path.getsize(path))
|
|
220
|
+
return path
|
|
221
|
+
|
|
222
|
+
|
|
202
223
|
def read_spectrum(fname, fmt=None):
|
|
203
224
|
if not os.path.exists(fname):
|
|
204
225
|
sys.exit("File %s not found" % fname)
|
|
@@ -270,7 +291,7 @@ def main():
|
|
|
270
291
|
ap = argparse.ArgumentParser(
|
|
271
292
|
prog="pyredshift",
|
|
272
293
|
usage="pyredshift [-help] [-f FORMAT] [-z REDSHIFT] [--retro] "
|
|
273
|
-
"[--microns]
|
|
294
|
+
"[--microns] file_or_URL",
|
|
274
295
|
description="Interactive redshifting of 1D spectra "
|
|
275
296
|
"(port of pdlredshift), v%s." % redshift_module.__version__,
|
|
276
297
|
formatter_class=argparse.RawDescriptionHelpFormatter,
|
|
@@ -278,7 +299,9 @@ def main():
|
|
|
278
299
|
# -h epilog and the '?' help page cannot drift apart
|
|
279
300
|
epilog=redshift_module.formats_text())
|
|
280
301
|
ap.add_argument("-help", action="help", help=argparse.SUPPRESS)
|
|
281
|
-
ap.add_argument("file",
|
|
302
|
+
ap.add_argument("file", metavar="file_or_URL",
|
|
303
|
+
help="spectrum file (FITS, CSV or 2-column ascii), "
|
|
304
|
+
"or an http(s)/ftp URL of one")
|
|
282
305
|
ap.add_argument("-f", "--format", default=None, metavar="FORMAT",
|
|
283
306
|
help="force the input format instead of auto-detecting")
|
|
284
307
|
ap.add_argument("-z", "--redshift", type=float, default=None,
|
|
@@ -292,14 +315,23 @@ def main():
|
|
|
292
315
|
help=argparse.SUPPRESS) # deprecated alias for --retro
|
|
293
316
|
args = ap.parse_args()
|
|
294
317
|
|
|
295
|
-
|
|
318
|
+
# A URL instead of a file: download to a temp file, label by its name
|
|
319
|
+
fname, label, tmp = args.file, os.path.basename(args.file), None
|
|
320
|
+
if re.match(r"^(https?|ftp)://", args.file, re.I):
|
|
321
|
+
from urllib.parse import urlparse
|
|
322
|
+
tmp = fname = fetch_url(args.file)
|
|
323
|
+
label = os.path.basename(urlparse(args.file).path) or args.file
|
|
324
|
+
|
|
325
|
+
wav, spec, has_wcs = read_spectrum(fname, args.format)
|
|
326
|
+
if tmp is not None:
|
|
327
|
+
os.unlink(tmp) # arrays are in memory; the download can go
|
|
296
328
|
|
|
297
329
|
if np.nanmax(wav) < 100 and has_wcs and not args.microns:
|
|
298
330
|
print(" Detected microns -> Angstroms (--microns to keep)")
|
|
299
331
|
wav = wav * 10000.0
|
|
300
332
|
|
|
301
333
|
z = redshift_module.redshift(wav, spec, args.redshift,
|
|
302
|
-
|
|
334
|
+
label, dark=args.retro)
|
|
303
335
|
if z is not None:
|
|
304
336
|
print("Final redshift = %.6g" % z)
|
|
305
337
|
|
|
@@ -13,7 +13,7 @@ from setuptools import setup
|
|
|
13
13
|
|
|
14
14
|
setup(
|
|
15
15
|
name="pyredshift",
|
|
16
|
-
version="1.
|
|
16
|
+
version="1.17",
|
|
17
17
|
description="Interactive redshifting of 1D astronomical spectra "
|
|
18
18
|
"(Python successor of pdlredshift / redshift.f)",
|
|
19
19
|
long_description=open("README.md").read(),
|
|
@@ -68,6 +68,16 @@ V1.14 - Saving works properly: the toolbar save button no longer
|
|
|
68
68
|
- Lineage/credits at the top of the help page.
|
|
69
69
|
V1.15 - Help-page credits link to the GitHub repo; lineage text in a
|
|
70
70
|
readable muted grey in both themes.
|
|
71
|
+
V1.16 - Bare modifier presses are no longer input: ESC shift-O works
|
|
72
|
+
(the 'shift' keydown used to be read as the shortcut key), a
|
|
73
|
+
stray shift can't consume the second pick of x/y/e/m or close
|
|
74
|
+
the line menu.
|
|
75
|
+
- matplotlib 3.11 compatibility: keep full-figure blitting on
|
|
76
|
+
when another axes overlaps (3.11 would silently disable it on
|
|
77
|
+
tall windows), manage the cursor background ourselves.
|
|
78
|
+
V1.17 - An http(s)/ftp URL may be given instead of a file: downloaded
|
|
79
|
+
to a temp file (extension kept so auto-detection works, deleted
|
|
80
|
+
once read), window labelled with the URL's filename.
|
|
71
81
|
"""
|
|
72
82
|
|
|
73
83
|
import ctypes
|
|
@@ -113,7 +123,7 @@ try:
|
|
|
113
123
|
except AttributeError:
|
|
114
124
|
pass
|
|
115
125
|
|
|
116
|
-
__version__ = "1.
|
|
126
|
+
__version__ = "1.17"
|
|
117
127
|
|
|
118
128
|
C_LIGHT = 2.99792458e8 # m/s
|
|
119
129
|
|
|
@@ -136,9 +146,11 @@ FORMAT_HELP = [
|
|
|
136
146
|
("csv", "comma-separated, header rows skipped"),
|
|
137
147
|
("ascii", "2-column text"),
|
|
138
148
|
]
|
|
139
|
-
FORMAT_NOTES = ("Default is auto-detection.
|
|
140
|
-
"
|
|
141
|
-
"
|
|
149
|
+
FORMAT_NOTES = ("Default is auto-detection. An http(s)/ftp URL may be given "
|
|
150
|
+
"instead of a file (downloaded to a temp file). Wavelengths "
|
|
151
|
+
"that look like microns are converted to Angstroms "
|
|
152
|
+
"(--microns keeps them); NaNs are treated as bad pixels "
|
|
153
|
+
"and plot as gaps.")
|
|
142
154
|
|
|
143
155
|
CONFIG_FILE = os.path.expanduser("~/.pyredshift.json") # remembers window size
|
|
144
156
|
DEFAULT_FIGSIZE = (13.0, 5.5) # inches
|
|
@@ -365,7 +377,19 @@ class StickyCursor(Cursor):
|
|
|
365
377
|
|
|
366
378
|
def __init__(self, ax_, **kwargs):
|
|
367
379
|
self._last_event = None
|
|
368
|
-
|
|
380
|
+
with warnings.catch_warnings():
|
|
381
|
+
# mpl 3.11 warns + disables useblit on overlapping axes;
|
|
382
|
+
# we re-assert it below, so don't let the warning through
|
|
383
|
+
warnings.simplefilter("ignore", UserWarning)
|
|
384
|
+
super().__init__(ax_, **kwargs)
|
|
385
|
+
# matplotlib 3.11 disables useblit when another axes overlaps (the
|
|
386
|
+
# '?' button can overlap on tall windows) - a guard our full-figure
|
|
387
|
+
# blit doesn't need; it also no longer initialises self.background
|
|
388
|
+
# (we manage it ourselves in clear())
|
|
389
|
+
self.useblit = self.canvas.supports_blit
|
|
390
|
+
self.linev.set_animated(self.useblit)
|
|
391
|
+
self.lineh.set_animated(self.useblit)
|
|
392
|
+
self.background = None
|
|
369
393
|
self.linev.set_clip_on(False) # let the crosshair escape the box
|
|
370
394
|
self.lineh.set_clip_on(False)
|
|
371
395
|
self.connect_event("draw_event", self._redraw)
|
|
@@ -380,9 +404,10 @@ class StickyCursor(Cursor):
|
|
|
380
404
|
self.background = self.canvas.copy_from_bbox(self.canvas.figure.bbox)
|
|
381
405
|
|
|
382
406
|
def onmove(self, event):
|
|
383
|
-
#
|
|
384
|
-
# check
|
|
385
|
-
#
|
|
407
|
+
# Based on Cursor.onmove from matplotlib 3.9, minus the widgetlock
|
|
408
|
+
# check, with whole-window coords and full-figure blitting. Checked
|
|
409
|
+
# against matplotlib 3.11 (which moved to _save/_load_blit_background
|
|
410
|
+
# helpers - we keep our own self.background instead).
|
|
386
411
|
if self.ignore(event):
|
|
387
412
|
return
|
|
388
413
|
xdata, ydata = surface_xy(self.ax, event)
|
|
@@ -443,6 +468,12 @@ class StickyCursor(Cursor):
|
|
|
443
468
|
update_readout(readout_lastev)
|
|
444
469
|
|
|
445
470
|
|
|
471
|
+
# Pressing a modifier fires its own key_press_event before the combination
|
|
472
|
+
# (ESC shift-O used to read the bare 'shift' as the shortcut key)
|
|
473
|
+
MODIFIER_KEYS = ("shift", "control", "ctrl", "alt", "cmd", "super", "meta",
|
|
474
|
+
"caps_lock", "fn")
|
|
475
|
+
|
|
476
|
+
|
|
446
477
|
def normkey(ch):
|
|
447
478
|
# Some backends report shifted letters as 'shift+b' - normalise to 'B'
|
|
448
479
|
if ch is not None and ch.startswith("shift+") and len(ch) == 7:
|
|
@@ -484,6 +515,8 @@ def pgband(allow_drag=False):
|
|
|
484
515
|
return surface_xy(ax, ev)
|
|
485
516
|
|
|
486
517
|
def on_key(ev):
|
|
518
|
+
if ev.key in MODIFIER_KEYS:
|
|
519
|
+
return # a bare modifier press is not input
|
|
487
520
|
xd, yd = data_xy(ev)
|
|
488
521
|
done(xd, yd, normkey(ev.key))
|
|
489
522
|
|
|
@@ -649,6 +682,8 @@ def line_menu(xd, yd):
|
|
|
649
682
|
fig.canvas.stop_event_loop()
|
|
650
683
|
|
|
651
684
|
def on_key(ev):
|
|
685
|
+
if ev.key in MODIFIER_KEYS:
|
|
686
|
+
return # don't let a bare shift press close the menu
|
|
652
687
|
state["picked"] = None
|
|
653
688
|
fig.canvas.stop_event_loop()
|
|
654
689
|
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: pyredshift
|
|
3
|
-
Version: 1.
|
|
3
|
+
Version: 1.17
|
|
4
4
|
Summary: Interactive redshifting of 1D astronomical spectra (Python successor of pdlredshift / redshift.f)
|
|
5
5
|
Home-page: https://github.com/karlglazebrook/pyredshift
|
|
6
6
|
Author: Karl Glazebrook
|
|
@@ -70,6 +70,7 @@ Requires python ≥ 3.9 with numpy, matplotlib, astropy and scipy.
|
|
|
70
70
|
|
|
71
71
|
```
|
|
72
72
|
pyredshift spectrum.fits # format auto-detected
|
|
73
|
+
pyredshift https://host/spectrum.fits # straight from an archive URL
|
|
73
74
|
pyredshift spectrum.fits -f sdss # force a format
|
|
74
75
|
pyredshift spectrum.fits -z 2.19 # start from a known redshift
|
|
75
76
|
pyredshift spectrum.fits --retro # retro PGPLOT-style black background
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|