plotastrodata 1.8.1__tar.gz → 1.8.3__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.
- {plotastrodata-1.8.1/plotastrodata.egg-info → plotastrodata-1.8.3}/PKG-INFO +1 -1
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/plotastrodata/__init__.py +1 -1
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/plotastrodata/noise_utils.py +18 -25
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/plotastrodata/other_utils.py +22 -0
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/plotastrodata/plot_utils.py +30 -56
- {plotastrodata-1.8.1 → plotastrodata-1.8.3/plotastrodata.egg-info}/PKG-INFO +1 -1
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/LICENSE +0 -0
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/MANIFEST.in +0 -0
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/README.md +0 -0
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/plotastrodata/analysis_utils.py +0 -0
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/plotastrodata/const_utils.py +0 -0
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/plotastrodata/coord_utils.py +0 -0
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/plotastrodata/ext_utils.py +0 -0
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/plotastrodata/fft_utils.py +0 -0
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/plotastrodata/fits_utils.py +0 -0
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/plotastrodata/fitting_utils.py +0 -0
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/plotastrodata/los_utils.py +0 -0
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/plotastrodata/matrix_utils.py +0 -0
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/plotastrodata.egg-info/SOURCES.txt +0 -0
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/plotastrodata.egg-info/dependency_links.txt +0 -0
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/plotastrodata.egg-info/not-zip-safe +0 -0
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/plotastrodata.egg-info/requires.txt +0 -0
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/plotastrodata.egg-info/top_level.txt +0 -0
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/setup.cfg +0 -0
- {plotastrodata-1.8.1 → plotastrodata-1.8.3}/setup.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: plotastrodata
|
|
3
|
-
Version: 1.8.
|
|
3
|
+
Version: 1.8.3
|
|
4
4
|
Summary: plotastrodata is a tool for astronomers to create figures from FITS files and perform fundamental data analyses with ease.
|
|
5
5
|
Home-page: https://github.com/yusukeaso-astron/plotastrodata
|
|
6
6
|
Download-URL: https://github.com/yusukeaso-astron/plotastrodata
|
|
@@ -4,6 +4,7 @@ import matplotlib.pyplot as plt
|
|
|
4
4
|
from scipy.special import erf
|
|
5
5
|
|
|
6
6
|
from plotastrodata.fitting_utils import EmceeCorner
|
|
7
|
+
from plotastrodata.other_utils import close_figure
|
|
7
8
|
|
|
8
9
|
|
|
9
10
|
def normalize(range: tuple = (-3.5, 3.5), bins: int = 100):
|
|
@@ -101,23 +102,23 @@ def select_noise(data: np.ndarray, sigma: str) -> np.ndarray:
|
|
|
101
102
|
|
|
102
103
|
|
|
103
104
|
class Noise:
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
'(no string)': calculate the mean and standard deviation.
|
|
105
|
+
"""This class holds the data selected as noise, histogram, and best-fit function.
|
|
106
|
+
The following methods are acceptable for data selection. Multiple options are possible.
|
|
107
|
+
'edge': use data[0] and data[-1].
|
|
108
|
+
'out': exclude inner 60% about axes=-2 and -1.
|
|
109
|
+
'neg': use only negative values.
|
|
110
|
+
'iter': exclude outliers.
|
|
111
|
+
The following methods are acceptable for noise estimation. Only single option is possible.
|
|
112
|
+
'med': calculate rms from the median of data^2 assuming Gaussian.
|
|
113
|
+
'hist': fit histgram with Gaussian.
|
|
114
|
+
'hist-pbcor': fit histgram with PB-corrected Gaussian.
|
|
115
|
+
'(no string)': calculate the mean and standard deviation.
|
|
116
116
|
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
117
|
+
Args:
|
|
118
|
+
data (np.ndarray): Original data array.
|
|
119
|
+
sigma (str): Methods above, like 'edge,neg,hist-pbcor'.
|
|
120
|
+
"""
|
|
121
|
+
def __init__(self, data: np.ndarray, sigma: str):
|
|
121
122
|
self.data = select_noise(data, sigma)
|
|
122
123
|
self.sigma = sigma
|
|
123
124
|
self.m0 = np.mean(self.data)
|
|
@@ -166,21 +167,13 @@ class Noise:
|
|
|
166
167
|
savefig (dict or str, optional): For plt.figure().savefig(). Defaults to None.
|
|
167
168
|
show (bool, optional): True means doing plt.show(). Defaults to False.
|
|
168
169
|
"""
|
|
169
|
-
savefig0 = {'bbox_inches': 'tight', 'transparent': True}
|
|
170
170
|
fig = plt.figure()
|
|
171
171
|
ax = fig.add_subplot(1, 1, 1)
|
|
172
172
|
ax.plot(self.hbin, self.hist, drawstyle='steps-mid')
|
|
173
173
|
ax.plot(self.hbin, self.model, '-')
|
|
174
174
|
ax.set_xlabel('(noise - m0) / s0')
|
|
175
175
|
ax.set_ylabel('Probability density')
|
|
176
|
-
fig
|
|
177
|
-
if savefig is not None:
|
|
178
|
-
s = {'fname': savefig} if type(savefig) is str else savefig
|
|
179
|
-
savefig0.update(s)
|
|
180
|
-
fig.savefig(**savefig0)
|
|
181
|
-
if show:
|
|
182
|
-
plt.show()
|
|
183
|
-
plt.close()
|
|
176
|
+
close_figure(fig, savefig, show)
|
|
184
177
|
|
|
185
178
|
|
|
186
179
|
def estimate_rms(data: np.ndarray,
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import numpy as np
|
|
2
|
+
import matplotlib.pyplot as plt
|
|
2
3
|
from scipy.interpolate import RegularGridInterpolator as RGI
|
|
3
4
|
|
|
4
5
|
from plotastrodata.matrix_utils import Mrot, dot2d
|
|
@@ -206,3 +207,24 @@ def gaussian2d(xy: np.ndarray,
|
|
|
206
207
|
s, t = dot2d(Mrot(-pa), [xy[1] - yo, xy[0] - xo])
|
|
207
208
|
g = amplitude * np.exp2(-4 * ((s / fwhm_major)**2 + (t / fwhm_minor)**2))
|
|
208
209
|
return g
|
|
210
|
+
|
|
211
|
+
|
|
212
|
+
def close_figure(fig: object,
|
|
213
|
+
savefig: dict | str | None = None,
|
|
214
|
+
show: bool = False) -> None:
|
|
215
|
+
"""Save, show, and close the figure.
|
|
216
|
+
|
|
217
|
+
Args:
|
|
218
|
+
fig (object): External plt.figure(). Defaults to None.
|
|
219
|
+
savefig (dict or str, optional): For plt.figure().savefig(). Defaults to None.
|
|
220
|
+
show (bool, optional): True means doing plt.show(). Defaults to False.
|
|
221
|
+
"""
|
|
222
|
+
savefig0 = {'bbox_inches': 'tight', 'transparent': True}
|
|
223
|
+
fig.tight_layout()
|
|
224
|
+
if savefig is not None:
|
|
225
|
+
s = {'fname': savefig} if type(savefig) is str else savefig
|
|
226
|
+
savefig0.update(s)
|
|
227
|
+
fig.savefig(**savefig0)
|
|
228
|
+
if show:
|
|
229
|
+
plt.show()
|
|
230
|
+
plt.close()
|
|
@@ -7,7 +7,7 @@ from dataclasses import dataclass
|
|
|
7
7
|
|
|
8
8
|
from plotastrodata.coord_utils import coord2xy, xy2coord
|
|
9
9
|
from plotastrodata.noise_utils import estimate_rms
|
|
10
|
-
from plotastrodata.other_utils import listing
|
|
10
|
+
from plotastrodata.other_utils import listing, close_figure
|
|
11
11
|
from plotastrodata.analysis_utils import AstroData, AstroFrame
|
|
12
12
|
|
|
13
13
|
|
|
@@ -271,6 +271,8 @@ def kwargs2AstroFrame(kw: dict) -> AstroFrame:
|
|
|
271
271
|
for k in vars(f):
|
|
272
272
|
if k in kw:
|
|
273
273
|
tmp[k] = kw[k]
|
|
274
|
+
if k not in ['fitsimage', 'center']:
|
|
275
|
+
del kw[k]
|
|
274
276
|
f = AstroFrame(**tmp)
|
|
275
277
|
return f
|
|
276
278
|
|
|
@@ -1169,7 +1171,6 @@ def plotprofile(coords: list[str] | str = [],
|
|
|
1169
1171
|
gaussfit: bool = False, gauss_kwargs: dict = {},
|
|
1170
1172
|
title: list[str] | None = None,
|
|
1171
1173
|
text: list[str] | None = None,
|
|
1172
|
-
dist: float = 1., vsys: float = 0.,
|
|
1173
1174
|
nrows: int = 0, ncols: int = 1,
|
|
1174
1175
|
fig: object | None = None,
|
|
1175
1176
|
ax: object | None = None,
|
|
@@ -1177,7 +1178,7 @@ def plotprofile(coords: list[str] | str = [],
|
|
|
1177
1178
|
savefig: dict | str | None = None,
|
|
1178
1179
|
show: bool = False,
|
|
1179
1180
|
**kwargs) -> tuple[object, object]:
|
|
1180
|
-
"""Use Axes.plot of matplotlib to plot line profiles at given coordinates. kwargs must include the arguments of AstroData to specify the data to be plotted. kwargs can include the arguments of PlotAxes2D to adjust x and y axes.
|
|
1181
|
+
"""Use Axes.plot of matplotlib to plot line profiles at given coordinates. kwargs must include the arguments of AstroData to specify the data to be plotted. kwargs must include the arguments of AstroFrame to specify the ranges and so on for plotting. kwargs can include the arguments of PlotAxes2D to adjust x and y axes.
|
|
1181
1182
|
|
|
1182
1183
|
Args:
|
|
1183
1184
|
coords (list, optional): Coordinates. Defaults to [].
|
|
@@ -1191,12 +1192,10 @@ def plotprofile(coords: list[str] | str = [],
|
|
|
1191
1192
|
gauss_kwargs (dict, optional): Kwargs for Axes.plot. Defaults to {}.
|
|
1192
1193
|
title (list, optional): For each plot. Defaults to None.
|
|
1193
1194
|
text (list, optional): For each plot. Defaults to None.
|
|
1194
|
-
dist (float, optional): Change x and y in arcsec to au. Defaults to 1..
|
|
1195
|
-
vsys (float, optional): Each channel shows v-vsys. Defaults to 0..
|
|
1196
1195
|
nrows (int, optional): Used for channel maps. Defaults to 0.
|
|
1197
1196
|
ncols (int, optional): Used for channel maps. Defaults to 1.
|
|
1198
|
-
fig (optional): External plt.figure(). Defaults to None.
|
|
1199
|
-
ax (optional): External fig.add_subplot(). Defaults to None.
|
|
1197
|
+
fig (object, optional): External plt.figure(). Defaults to None.
|
|
1198
|
+
ax (object, optional): External fig.add_subplot(). Defaults to None.
|
|
1200
1199
|
getfigax (bool, optional): Defaults to False.
|
|
1201
1200
|
savefig (dict or str, optional): For plt.figure().savefig(). Defaults to None.
|
|
1202
1201
|
show (bool, optional): True means doing plt.show(). Defaults to False.
|
|
@@ -1208,13 +1207,10 @@ def plotprofile(coords: list[str] | str = [],
|
|
|
1208
1207
|
_kw.update(kwargs)
|
|
1209
1208
|
_kwgauss = {'drawstyle': 'default', 'color': 'g'}
|
|
1210
1209
|
_kwgauss.update(gauss_kwargs)
|
|
1211
|
-
savefig0 = {'bbox_inches': 'tight', 'transparent': True}
|
|
1212
1210
|
if type(coords) is str:
|
|
1213
1211
|
coords = [coords]
|
|
1214
|
-
|
|
1215
|
-
f = AstroFrame(dist=dist, vsys=vsys, vmin=vmin, vmax=vmax)
|
|
1212
|
+
f = kwargs2AstroFrame(_kw)
|
|
1216
1213
|
d = kwargs2AstroData(_kw)
|
|
1217
|
-
Tb = d.Tb
|
|
1218
1214
|
f.read(d)
|
|
1219
1215
|
d.binning([width, 1, 1])
|
|
1220
1216
|
v, prof, gfitres = d.profile(coords=coords, xlist=xlist, ylist=ylist,
|
|
@@ -1223,7 +1219,7 @@ def plotprofile(coords: list[str] | str = [],
|
|
|
1223
1219
|
nprof = len(prof)
|
|
1224
1220
|
if 'ylabel' in _kw:
|
|
1225
1221
|
ylabel = _kw['ylabel']
|
|
1226
|
-
elif Tb:
|
|
1222
|
+
elif d.Tb:
|
|
1227
1223
|
ylabel = r'$T_b$ (K)'
|
|
1228
1224
|
elif flux:
|
|
1229
1225
|
ylabel = 'Flux (Jy)'
|
|
@@ -1249,7 +1245,7 @@ def plotprofile(coords: list[str] | str = [],
|
|
|
1249
1245
|
if 'xlim' not in _kw:
|
|
1250
1246
|
_kw['xlim'] = [v.min(), v.max()]
|
|
1251
1247
|
_kw['samexy'] = False
|
|
1252
|
-
|
|
1248
|
+
pa2 = kwargs2PlotAxes2D(_kw)
|
|
1253
1249
|
for i in range(nprof):
|
|
1254
1250
|
sharex = None if i < nrows - 1 else ax[i - 1]
|
|
1255
1251
|
ax[i] = fig.add_subplot(nrows, ncols, i + 1, sharex=sharex)
|
|
@@ -1258,7 +1254,7 @@ def plotprofile(coords: list[str] | str = [],
|
|
|
1258
1254
|
ax[i].plot(v, prof[i], **_kw)
|
|
1259
1255
|
ax[i].hlines([0], v.min(), v.max(), linestyle='dashed', color='k')
|
|
1260
1256
|
ax[i].set_ylabel(ylabel[i])
|
|
1261
|
-
|
|
1257
|
+
pa2.set_xyaxes(ax[i])
|
|
1262
1258
|
if text is not None:
|
|
1263
1259
|
ax[i].text(**text[i])
|
|
1264
1260
|
if title is not None:
|
|
@@ -1269,38 +1265,25 @@ def plotprofile(coords: list[str] | str = [],
|
|
|
1269
1265
|
plt.setp(ax[i].get_xticklabels(), visible=False)
|
|
1270
1266
|
if getfigax:
|
|
1271
1267
|
return fig, ax
|
|
1272
|
-
|
|
1273
|
-
|
|
1274
|
-
s = {'fname': savefig} if type(savefig) is str else savefig
|
|
1275
|
-
savefig0.update(s)
|
|
1276
|
-
fig.savefig(**savefig0)
|
|
1277
|
-
if show:
|
|
1278
|
-
plt.show()
|
|
1279
|
-
plt.close()
|
|
1268
|
+
|
|
1269
|
+
close_figure(fig, savefig, show)
|
|
1280
1270
|
|
|
1281
1271
|
|
|
1282
1272
|
def plotslice(length: float, dx: float | None = None, pa: float = 0,
|
|
1283
|
-
dist: float = 1, xoff: float = 0, yoff: float = 0,
|
|
1284
|
-
xflip: bool = True, yflip: bool = False,
|
|
1285
1273
|
txtfile: str | None = None,
|
|
1286
1274
|
fig: object | None = None, ax: object | None = None,
|
|
1287
1275
|
getfigax: bool = False,
|
|
1288
1276
|
savefig: str | dict | None = None, show: bool = False,
|
|
1289
|
-
**kwargs) ->
|
|
1290
|
-
"""Use Axes.plot of matplotlib to plot a 1D spatial slice in a 2D map. kwargs must include the arguments of AstroData to specify the data to be plotted. kwargs can include the arguments of PlotAxes2D to adjust x and y axes.
|
|
1277
|
+
**kwargs) -> tuple[object, object]:
|
|
1278
|
+
"""Use Axes.plot of matplotlib to plot a 1D spatial slice in a 2D map. kwargs must include the arguments of AstroData to specify the data to be plotted. kwargs must include the arguments of AstroFrame to specify the ranges and so on for plotting. kwargs can include the arguments of PlotAxes2D to adjust x and y axes.
|
|
1291
1279
|
|
|
1292
1280
|
Args:
|
|
1293
1281
|
length (float): Slice length.
|
|
1294
1282
|
dx (float, optional): Grid increment. Defaults to None.
|
|
1295
1283
|
pa (float, optional): Degree. Position angle. Defaults to 0.
|
|
1296
|
-
dist (float, optional): For AstroFrame. Defaults to 1.
|
|
1297
|
-
xoff (float, optional): For AstroFrame. Defaults to 0.
|
|
1298
|
-
yoff (float, optional): For AstroFrame. Defaults to 0.
|
|
1299
|
-
xflip (bool, optional): For AstroFrame. Defaults to True.
|
|
1300
|
-
yflip (bool, optional): For AstroFrame. Defaults to False.
|
|
1301
1284
|
txtfile (str, optional): File name for numpy.savetxt(). Defaults to None.
|
|
1302
|
-
fig (optional): External plt.figure(). Defaults to None.
|
|
1303
|
-
ax (optional): External fig.add_subplot(). Defaults to None.
|
|
1285
|
+
fig (object, optional): External plt.figure(). Defaults to None.
|
|
1286
|
+
ax (object, optional): External fig.add_subplot(). Defaults to None.
|
|
1304
1287
|
getfigax (bool, optional): Defaults to False.
|
|
1305
1288
|
savefig (dict or str, optional): For plt.figure().savefig(). Defaults to None.
|
|
1306
1289
|
show (bool, optional): True means doing plt.show(). Defaults to False.
|
|
@@ -1310,31 +1293,23 @@ def plotslice(length: float, dx: float | None = None, pa: float = 0,
|
|
|
1310
1293
|
"""
|
|
1311
1294
|
_kw = {'linestyle': '-', 'marker': 'o'}
|
|
1312
1295
|
_kw.update(kwargs)
|
|
1313
|
-
|
|
1314
|
-
|
|
1315
|
-
f = AstroFrame(rmax=length / 2, dist=dist, xoff=xoff, yoff=yoff,
|
|
1316
|
-
xflip=xflip, yflip=yflip, center=center)
|
|
1296
|
+
_kw['rmax'] = length / 2
|
|
1297
|
+
f = kwargs2AstroFrame(_kw)
|
|
1317
1298
|
d = kwargs2AstroData(_kw)
|
|
1318
|
-
Tb = d.Tb
|
|
1319
1299
|
f.read(d)
|
|
1320
1300
|
if np.ndim(d.data) > 2:
|
|
1321
1301
|
print('Only 2D map is supported.')
|
|
1322
1302
|
return
|
|
1323
1303
|
|
|
1324
1304
|
r, z = d.slice(length=length, pa=pa, dx=dx)
|
|
1325
|
-
xunit = 'arcsec' if dist == 1 else 'au'
|
|
1326
|
-
yunit = 'K' if Tb else d.bunit
|
|
1327
|
-
yquantity = '
|
|
1305
|
+
xunit = 'arcsec' if f.dist == 1 else 'au'
|
|
1306
|
+
yunit = 'K' if d.Tb else d.bunit
|
|
1307
|
+
yquantity = r'$T_b$' if d.Tb else 'intensity'
|
|
1328
1308
|
|
|
1329
1309
|
if txtfile is not None:
|
|
1330
1310
|
np.savetxt(txtfile, np.c_[r, z],
|
|
1331
1311
|
header=f'x ({xunit}), {yquantity} ({yunit}); '
|
|
1332
1312
|
+ f'positive x is pa={pa:.2f} deg.')
|
|
1333
|
-
set_rcparams()
|
|
1334
|
-
if fig is None:
|
|
1335
|
-
fig = plt.figure()
|
|
1336
|
-
if ax is None:
|
|
1337
|
-
ax = fig.add_subplot(1, 1, 1)
|
|
1338
1313
|
if 'xlabel' not in _kw:
|
|
1339
1314
|
_kw['xlabel'] = f'Offset ({xunit})'
|
|
1340
1315
|
if 'ylabel' not in _kw:
|
|
@@ -1342,21 +1317,20 @@ def plotslice(length: float, dx: float | None = None, pa: float = 0,
|
|
|
1342
1317
|
if 'xlim' not in _kw:
|
|
1343
1318
|
_kw['xlim'] = [r.min(), r.max()]
|
|
1344
1319
|
_kw['samexy'] = False
|
|
1345
|
-
|
|
1320
|
+
set_rcparams()
|
|
1321
|
+
if fig is None:
|
|
1322
|
+
fig = plt.figure()
|
|
1323
|
+
if ax is None:
|
|
1324
|
+
ax = fig.add_subplot(1, 1, 1)
|
|
1325
|
+
pa2 = kwargs2PlotAxes2D(_kw)
|
|
1346
1326
|
ax.plot(r, z, **_kw)
|
|
1347
1327
|
if d.sigma is not None:
|
|
1348
1328
|
ax.plot(r, r * 0 + 3 * d.sigma, 'k--')
|
|
1349
|
-
|
|
1329
|
+
pa2.set_xyaxes(ax)
|
|
1350
1330
|
if getfigax:
|
|
1351
1331
|
return fig, ax
|
|
1352
|
-
|
|
1353
|
-
|
|
1354
|
-
s = {'fname': savefig} if type(savefig) is str else savefig
|
|
1355
|
-
savefig0.update(s)
|
|
1356
|
-
fig.savefig(**savefig0)
|
|
1357
|
-
if show:
|
|
1358
|
-
plt.show()
|
|
1359
|
-
plt.close()
|
|
1332
|
+
|
|
1333
|
+
close_figure(fig, savefig, show)
|
|
1360
1334
|
|
|
1361
1335
|
|
|
1362
1336
|
def plot3d(levels: list[float] = [3, 6, 12],
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: plotastrodata
|
|
3
|
-
Version: 1.8.
|
|
3
|
+
Version: 1.8.3
|
|
4
4
|
Summary: plotastrodata is a tool for astronomers to create figures from FITS files and perform fundamental data analyses with ease.
|
|
5
5
|
Home-page: https://github.com/yusukeaso-astron/plotastrodata
|
|
6
6
|
Download-URL: https://github.com/yusukeaso-astron/plotastrodata
|
|
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
|
|
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
|