rubycond_cb 0.2.0__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.
- rubycond_cb-0.2.0/PKG-INFO +85 -0
- rubycond_cb-0.2.0/README.md +61 -0
- rubycond_cb-0.2.0/pyproject.toml +32 -0
- rubycond_cb-0.2.0/rubycond_CB/example/Neon_data.npy +0 -0
- rubycond_cb-0.2.0/rubycond_CB/model/CB_Model.py +277 -0
- rubycond_cb-0.2.0/rubycond_CB/model/Neon_Astrosurf.csv +25 -0
- rubycond_cb-0.2.0/rubycond_CB/model/Neon_PI.csv +20 -0
- rubycond_cb-0.2.0/rubycond_CB/rubycond_CB.py +549 -0
- rubycond_cb-0.2.0/rubycond_CB/view/CB_View.py +992 -0
- rubycond_cb-0.2.0/rubycond_CB/view/CB_about.py +237 -0
- rubycond_cb-0.2.0/rubycond_CB/view/CB_calib_controls.py +278 -0
- rubycond_cb-0.2.0/rubycond_CB/view/logo_CP_Scaled.png +0 -0
- rubycond_cb-0.2.0/rubycond_CB/view/logo_IMPMC_Scaled.png +0 -0
- rubycond_cb-0.2.0/rubycond_CB/view/manual.pdf +0 -0
|
@@ -0,0 +1,85 @@
|
|
|
1
|
+
Metadata-Version: 2.3
|
|
2
|
+
Name: rubycond_cb
|
|
3
|
+
Version: 0.2.0
|
|
4
|
+
Summary: Tool for calibrating a spectrometer wavelengths
|
|
5
|
+
License: GPL-3.0-or-later
|
|
6
|
+
Author: Yiuri Garino
|
|
7
|
+
Author-email: yiuri.garino@cnrs.fr
|
|
8
|
+
Requires-Python: >=3.11
|
|
9
|
+
Classifier: License :: OSI Approved :: GNU General Public License v3 or later (GPLv3+)
|
|
10
|
+
Classifier: Programming Language :: Python :: 3
|
|
11
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
12
|
+
Classifier: Programming Language :: Python :: 3.12
|
|
13
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
14
|
+
Requires-Dist: configparser (>=6,<7)
|
|
15
|
+
Requires-Dist: lmfit (>=1.3,<2.0)
|
|
16
|
+
Requires-Dist: matplotlib (>=3.8.2,<4.0.0)
|
|
17
|
+
Requires-Dist: numpy (>=2.1,<3.0.0)
|
|
18
|
+
Requires-Dist: pillow (>=10.1.0)
|
|
19
|
+
Requires-Dist: pyqt5 (>=5.15.11,<6.0.0)
|
|
20
|
+
Requires-Dist: rubycond_of (>=0.1.0)
|
|
21
|
+
Project-URL: Repository, https://github.com/CelluleProjet/Rubycond_CB
|
|
22
|
+
Description-Content-Type: text/markdown
|
|
23
|
+
|
|
24
|
+
# Rubycond_CB
|
|
25
|
+
Tool for calibrating the spectrometer wavelengths
|
|
26
|
+
|
|
27
|
+
<img width="1282" height="702" alt="1_open_file" src="https://github.com/user-attachments/assets/3d744deb-cf81-4d27-aae1-8c685986c98d" />
|
|
28
|
+
|
|
29
|
+
# Manual
|
|
30
|
+
|
|
31
|
+
1) Select the Neon line on the left graph and the corresponding peak on the right graph.
|
|
32
|
+
The program automatically performs a peak fit within the pixel window defined in Delta (pixels), default 20 pixels.
|
|
33
|
+
|
|
34
|
+
2) Add the pair of points using the **ADD** button. The points used for calibration are indicated on both the graphs and the table on the left.
|
|
35
|
+
<img width="1920" height="1032" alt="2_1_point" src="https://github.com/user-attachments/assets/7078a113-a26a-4ff4-9c1e-c06ab30deee6" />
|
|
36
|
+
|
|
37
|
+
3) Repeat the operation, adding as many peaks as possible.
|
|
38
|
+
<img width="1920" height="1032" alt="3_n_point" src="https://github.com/user-attachments/assets/d46ac124-a0f3-407e-87d8-41a6133e65b5" />
|
|
39
|
+
|
|
40
|
+
4) Use the **Simple Calib** button to perform the calibration.
|
|
41
|
+
The calibration result is displayed in the left graph, and the fit result is shown in the Fit Output window.
|
|
42
|
+
<img width="1920" height="1032" alt="4_output" src="https://github.com/user-attachments/assets/689a1baa-e4ec-4fb9-97c4-5956a9384e15" />
|
|
43
|
+
|
|
44
|
+
5) Use the **Accept** button to send the calibration parameters to the main program
|
|
45
|
+
# Install
|
|
46
|
+
Use pip to install the program **within a virtual environment (strongly recommended).**
|
|
47
|
+
[Here's a short tutorial on installing a virtual environment.](https://github.com/CelluleProjet/Install/tree/main?tab=readme-ov-file#install-virtual-environment)
|
|
48
|
+
```bash
|
|
49
|
+
pip install rubycond_CB
|
|
50
|
+
```
|
|
51
|
+
# About
|
|
52
|
+
## Author
|
|
53
|
+
|
|
54
|
+
**Yiuri Garino**
|
|
55
|
+
|
|
56
|
+
## Contacts
|
|
57
|
+
|
|
58
|
+
**Yiuri Garino**
|
|
59
|
+
- yiuri.garino@cnrs.fr
|
|
60
|
+
|
|
61
|
+
**Silvia Boccato**
|
|
62
|
+
- silvia.boccato@cnrs.fr
|
|
63
|
+
|
|
64
|
+
<img src="https://github.com/CelluleProjet/Rubycond/assets/83216683/b728fe64-2752-4ecd-843b-09d335cf4f93" width="100" height="100">
|
|
65
|
+
<img src="https://github.com/CelluleProjet/Rubycond/assets/83216683/0a81ce1f-089f-49d8-ae65-d19af8078492" width="100" height="100">
|
|
66
|
+
|
|
67
|
+
|
|
68
|
+
[Cellule Projet](http://impmc.sorbonne-universite.fr/fr/plateformes-et-equipements/cellule-projet.html) @ [IMPMC](http://impmc.sorbonne-universite.fr/en/index.html)
|
|
69
|
+
|
|
70
|
+
|
|
71
|
+
## License
|
|
72
|
+
**Rubycond_CB**: Tool for calibrating the spectrometer wavelengths
|
|
73
|
+
|
|
74
|
+
|
|
75
|
+
Copyright (c) 2022-2026 Yiuri Garino
|
|
76
|
+
|
|
77
|
+
**Rubycond_CB** is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
|
|
78
|
+
This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
|
|
79
|
+
|
|
80
|
+
You should have received a copy of the GNU General Public License along with this program. If not, see <https://www.gnu.org/licenses/>.
|
|
81
|
+
|
|
82
|
+
## Release notes
|
|
83
|
+
|
|
84
|
+
Version 0.2.0 Release 260301: First release
|
|
85
|
+
|
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
# Rubycond_CB
|
|
2
|
+
Tool for calibrating the spectrometer wavelengths
|
|
3
|
+
|
|
4
|
+
<img width="1282" height="702" alt="1_open_file" src="https://github.com/user-attachments/assets/3d744deb-cf81-4d27-aae1-8c685986c98d" />
|
|
5
|
+
|
|
6
|
+
# Manual
|
|
7
|
+
|
|
8
|
+
1) Select the Neon line on the left graph and the corresponding peak on the right graph.
|
|
9
|
+
The program automatically performs a peak fit within the pixel window defined in Delta (pixels), default 20 pixels.
|
|
10
|
+
|
|
11
|
+
2) Add the pair of points using the **ADD** button. The points used for calibration are indicated on both the graphs and the table on the left.
|
|
12
|
+
<img width="1920" height="1032" alt="2_1_point" src="https://github.com/user-attachments/assets/7078a113-a26a-4ff4-9c1e-c06ab30deee6" />
|
|
13
|
+
|
|
14
|
+
3) Repeat the operation, adding as many peaks as possible.
|
|
15
|
+
<img width="1920" height="1032" alt="3_n_point" src="https://github.com/user-attachments/assets/d46ac124-a0f3-407e-87d8-41a6133e65b5" />
|
|
16
|
+
|
|
17
|
+
4) Use the **Simple Calib** button to perform the calibration.
|
|
18
|
+
The calibration result is displayed in the left graph, and the fit result is shown in the Fit Output window.
|
|
19
|
+
<img width="1920" height="1032" alt="4_output" src="https://github.com/user-attachments/assets/689a1baa-e4ec-4fb9-97c4-5956a9384e15" />
|
|
20
|
+
|
|
21
|
+
5) Use the **Accept** button to send the calibration parameters to the main program
|
|
22
|
+
# Install
|
|
23
|
+
Use pip to install the program **within a virtual environment (strongly recommended).**
|
|
24
|
+
[Here's a short tutorial on installing a virtual environment.](https://github.com/CelluleProjet/Install/tree/main?tab=readme-ov-file#install-virtual-environment)
|
|
25
|
+
```bash
|
|
26
|
+
pip install rubycond_CB
|
|
27
|
+
```
|
|
28
|
+
# About
|
|
29
|
+
## Author
|
|
30
|
+
|
|
31
|
+
**Yiuri Garino**
|
|
32
|
+
|
|
33
|
+
## Contacts
|
|
34
|
+
|
|
35
|
+
**Yiuri Garino**
|
|
36
|
+
- yiuri.garino@cnrs.fr
|
|
37
|
+
|
|
38
|
+
**Silvia Boccato**
|
|
39
|
+
- silvia.boccato@cnrs.fr
|
|
40
|
+
|
|
41
|
+
<img src="https://github.com/CelluleProjet/Rubycond/assets/83216683/b728fe64-2752-4ecd-843b-09d335cf4f93" width="100" height="100">
|
|
42
|
+
<img src="https://github.com/CelluleProjet/Rubycond/assets/83216683/0a81ce1f-089f-49d8-ae65-d19af8078492" width="100" height="100">
|
|
43
|
+
|
|
44
|
+
|
|
45
|
+
[Cellule Projet](http://impmc.sorbonne-universite.fr/fr/plateformes-et-equipements/cellule-projet.html) @ [IMPMC](http://impmc.sorbonne-universite.fr/en/index.html)
|
|
46
|
+
|
|
47
|
+
|
|
48
|
+
## License
|
|
49
|
+
**Rubycond_CB**: Tool for calibrating the spectrometer wavelengths
|
|
50
|
+
|
|
51
|
+
|
|
52
|
+
Copyright (c) 2022-2026 Yiuri Garino
|
|
53
|
+
|
|
54
|
+
**Rubycond_CB** is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
|
|
55
|
+
This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
|
|
56
|
+
|
|
57
|
+
You should have received a copy of the GNU General Public License along with this program. If not, see <https://www.gnu.org/licenses/>.
|
|
58
|
+
|
|
59
|
+
## Release notes
|
|
60
|
+
|
|
61
|
+
Version 0.2.0 Release 260301: First release
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
[project]
|
|
2
|
+
name = "rubycond_cb"
|
|
3
|
+
version = "0.2.0"
|
|
4
|
+
description = "Tool for calibrating a spectrometer wavelengths "
|
|
5
|
+
authors = [
|
|
6
|
+
{name = "Yiuri Garino", email = "yiuri.garino@cnrs.fr"}
|
|
7
|
+
]
|
|
8
|
+
license = "GPL-3.0-or-later"
|
|
9
|
+
readme = "README.md"
|
|
10
|
+
requires-python = ">=3.11"
|
|
11
|
+
dependencies = [
|
|
12
|
+
"numpy (>=2.1,<3.0.0)",
|
|
13
|
+
"configparser (>=6,<7)",
|
|
14
|
+
"matplotlib (>=3.8.2,<4.0.0)",
|
|
15
|
+
"lmfit (>=1.3,<2.0)",
|
|
16
|
+
"pyqt5 (>=5.15.11,<6.0.0)",
|
|
17
|
+
"pillow (>=10.1.0)",
|
|
18
|
+
"rubycond_of (>=0.1.0)"
|
|
19
|
+
]
|
|
20
|
+
|
|
21
|
+
[tool.poetry]
|
|
22
|
+
packages = [{ include = "rubycond_CB" }]
|
|
23
|
+
|
|
24
|
+
[project.urls]
|
|
25
|
+
repository = "https://github.com/CelluleProjet/Rubycond_CB"
|
|
26
|
+
|
|
27
|
+
[project.scripts]
|
|
28
|
+
rubycond_CB = "rubycond_CB.rubycond_CB:main"
|
|
29
|
+
|
|
30
|
+
[build-system]
|
|
31
|
+
requires = ["poetry-core>=2.0.0,<3.0.0"]
|
|
32
|
+
build-backend = "poetry.core.masonry.api"
|
|
Binary file
|
|
@@ -0,0 +1,277 @@
|
|
|
1
|
+
# -*- coding: utf-8 -*-
|
|
2
|
+
"""
|
|
3
|
+
|
|
4
|
+
Title: Rubycond_CB: tool for calibrating the wavelength of the spectrometer
|
|
5
|
+
|
|
6
|
+
This file is part of Rubycond: Pressure by Ruby Luminescence (PRL) software to determine pressure in diamond anvil cell experiments.
|
|
7
|
+
|
|
8
|
+
Version 0.2.0
|
|
9
|
+
Release 260301
|
|
10
|
+
|
|
11
|
+
Author:
|
|
12
|
+
|
|
13
|
+
Yiuri Garino
|
|
14
|
+
yiuri.garino@cnrs.fr
|
|
15
|
+
|
|
16
|
+
Copyright (c) 2023-2026 Yiuri Garino
|
|
17
|
+
|
|
18
|
+
Download:
|
|
19
|
+
https://github.com/CelluleProjet/Rubycond_calc
|
|
20
|
+
|
|
21
|
+
License: GPLv3
|
|
22
|
+
|
|
23
|
+
This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
|
|
24
|
+
This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
|
|
25
|
+
You should have received a copy of the GNU General Public License along with this program. If not, see <https://www.gnu.org/licenses/>.
|
|
26
|
+
|
|
27
|
+
"""
|
|
28
|
+
|
|
29
|
+
def reset():
|
|
30
|
+
import sys
|
|
31
|
+
|
|
32
|
+
if hasattr(sys, 'ps1'):
|
|
33
|
+
|
|
34
|
+
#clean Console and Memory
|
|
35
|
+
from IPython import get_ipython
|
|
36
|
+
get_ipython().run_line_magic('clear','/')
|
|
37
|
+
get_ipython().run_line_magic('reset','-sf')
|
|
38
|
+
print("Running interactively")
|
|
39
|
+
print()
|
|
40
|
+
terminal = False
|
|
41
|
+
else:
|
|
42
|
+
print("Running in terminal")
|
|
43
|
+
print()
|
|
44
|
+
terminal = True
|
|
45
|
+
|
|
46
|
+
if __name__ == '__main__':
|
|
47
|
+
reset()
|
|
48
|
+
|
|
49
|
+
import configparser as cp
|
|
50
|
+
from pathlib import Path
|
|
51
|
+
import numpy as np
|
|
52
|
+
import matplotlib.pyplot as plt
|
|
53
|
+
import os
|
|
54
|
+
from datetime import datetime
|
|
55
|
+
from lmfit.models import LinearModel, GaussianModel, PolynomialModel
|
|
56
|
+
from PyQt5 import QtWidgets, QtCore, QtGui
|
|
57
|
+
from scipy.special import wofz
|
|
58
|
+
from scipy.interpolate import Akima1DInterpolator
|
|
59
|
+
from pathlib import Path
|
|
60
|
+
|
|
61
|
+
SCRIPT_DIR = os.path.dirname(os.path.abspath(__file__))
|
|
62
|
+
|
|
63
|
+
class my_model():
|
|
64
|
+
def __init__(self, debug = False):
|
|
65
|
+
self.debug = debug
|
|
66
|
+
self.version = 'RC_Model_11.py'
|
|
67
|
+
if self.debug: print('\nModel\n')
|
|
68
|
+
try:
|
|
69
|
+
#file_NEON = Path("Neon_Astrosurf.csv")
|
|
70
|
+
file_NEON = Path("Neon_PI.csv")
|
|
71
|
+
path_NEON = Path(__file__).parent.resolve() / file_NEON
|
|
72
|
+
except:
|
|
73
|
+
path_NEON = file_NEON
|
|
74
|
+
|
|
75
|
+
|
|
76
|
+
self.Neon_lines = np.loadtxt(path_NEON, delimiter=',')
|
|
77
|
+
self.peaks_data_x = np.zeros((2,2)) #Data from open file
|
|
78
|
+
self.peaks_data_y = np.zeros((2,2)) #Data from open file
|
|
79
|
+
self.peaks_data_x_simple_calib = np.zeros((2,2))
|
|
80
|
+
|
|
81
|
+
self.fit_delta_pixel = .6
|
|
82
|
+
|
|
83
|
+
self.Last_peaks_pixel_clicked = 0
|
|
84
|
+
|
|
85
|
+
|
|
86
|
+
self.delta = 20
|
|
87
|
+
self.calib_cn = [0,0,0,0] #max poly degree = 3
|
|
88
|
+
|
|
89
|
+
#
|
|
90
|
+
self.statusbar_message_ref = [print] #List of messages method (print, label, statusbar, etc)
|
|
91
|
+
|
|
92
|
+
def statusbar_message_add(self, method):
|
|
93
|
+
#print(method)
|
|
94
|
+
self.statusbar_message_ref.append(method)
|
|
95
|
+
|
|
96
|
+
def nearest_neon(self, value):
|
|
97
|
+
if value is not None:
|
|
98
|
+
i = abs(self.Neon_lines[:,0]-value).argmin()
|
|
99
|
+
data = self.Neon_lines[i]
|
|
100
|
+
#print(self.Neon_lines)
|
|
101
|
+
#print(abs(self.Neon_lines-value))
|
|
102
|
+
if self.debug :
|
|
103
|
+
print(f'input {i}: {value}')
|
|
104
|
+
print(f'output : {data}')
|
|
105
|
+
else:
|
|
106
|
+
data = 0
|
|
107
|
+
return data
|
|
108
|
+
|
|
109
|
+
def peaks_data_pixel(self, value):
|
|
110
|
+
if value is not None:
|
|
111
|
+
data = abs(self.peaks_data_x-value).argmin()
|
|
112
|
+
|
|
113
|
+
|
|
114
|
+
#print(abs(self.Neon_lines-value))
|
|
115
|
+
if self.debug :
|
|
116
|
+
print(self.peaks_data_x)
|
|
117
|
+
print(f'input : {value}')
|
|
118
|
+
print(f'output : {data}')
|
|
119
|
+
else:
|
|
120
|
+
data = 0
|
|
121
|
+
return data
|
|
122
|
+
|
|
123
|
+
def button_calc_simple_calib(self):
|
|
124
|
+
y1 = self.Neon_Left_reference
|
|
125
|
+
y2 = self.Neon_Right_reference
|
|
126
|
+
x1 = self.Peaks_Left_reference
|
|
127
|
+
x2 = self.Peaks_Right_reference
|
|
128
|
+
s = (y2 - y1)/(x2 - x1)
|
|
129
|
+
i = y1 - s*x1
|
|
130
|
+
size = len(self.peaks_data_x)
|
|
131
|
+
pixels = np.arange(0,size,1)
|
|
132
|
+
if self.debug :
|
|
133
|
+
print(f'slope : {s}')
|
|
134
|
+
print(f'intercept : {i}')
|
|
135
|
+
self.peaks_data_x_simple_calib = i + s*pixels
|
|
136
|
+
|
|
137
|
+
def format_fit_results(self, degree, res):
|
|
138
|
+
message = 'Fit Output\n'
|
|
139
|
+
message+= '\n'
|
|
140
|
+
# message+= 'Wavelengths (nm) = c0 + c1 * pixels + c2 * pixels\u00B2 + c3 * pixels\u00B3\n'
|
|
141
|
+
# message+= '\n\n'
|
|
142
|
+
for i in range(degree+1):
|
|
143
|
+
|
|
144
|
+
message+= f'c{i} = '
|
|
145
|
+
message+= f"{res.params[f'line_c{i}'].value:.5e}"
|
|
146
|
+
message+= '\n'
|
|
147
|
+
self.calib_cn[i] = res.params[f'line_c{i}'].value
|
|
148
|
+
for j in range(3 - degree):
|
|
149
|
+
message+= f'c{j + degree +1} = 0'
|
|
150
|
+
message+= '\n'
|
|
151
|
+
self.calib_cn[j + degree +1] = 0
|
|
152
|
+
print(message)
|
|
153
|
+
print(self.calib_cn)
|
|
154
|
+
self.print_message_output = message
|
|
155
|
+
|
|
156
|
+
def calib_poly_3(self, data_x, data_y):
|
|
157
|
+
degree = min(len(data_x)-1, 3)
|
|
158
|
+
model = PolynomialModel(degree=degree, prefix='line_')
|
|
159
|
+
pars = model.guess(data_y, data_x)
|
|
160
|
+
res = model.fit(data_y, pars, x = data_x)
|
|
161
|
+
if self.debug: pars.pretty_print()
|
|
162
|
+
#if self.debug: res.fit_report()#TODO restore in next version
|
|
163
|
+
print(res.fit_report()) #TODO cut in next version
|
|
164
|
+
size = len(self.peaks_data_x)
|
|
165
|
+
pixels = np.arange(0,size,1)
|
|
166
|
+
|
|
167
|
+
self.peaks_data_x_simple_calib = model.eval(res.params, x = pixels)
|
|
168
|
+
|
|
169
|
+
#prepare message to be used in layout_Output
|
|
170
|
+
self.format_fit_results(degree, res)
|
|
171
|
+
|
|
172
|
+
def fit_peak_range(self):
|
|
173
|
+
try:
|
|
174
|
+
center = self.Last_peaks_pixel_clicked
|
|
175
|
+
delta = self.delta
|
|
176
|
+
data_x_graph = self.peaks_data_x[center - delta: center + delta + 1]
|
|
177
|
+
data_x_pixel = np.linspace(center - delta, center + delta, delta*2+1)
|
|
178
|
+
data_y = self.peaks_data_y[center - delta: center + delta + 1]
|
|
179
|
+
data_x, data_y, init, fit_x, fit_y, res = self.fit_peak(data_x_pixel, data_y)
|
|
180
|
+
|
|
181
|
+
spl = Akima1DInterpolator(data_x_pixel, data_x_graph)
|
|
182
|
+
|
|
183
|
+
data_x = spl(data_x)
|
|
184
|
+
fit_x = spl(fit_x)
|
|
185
|
+
center_pixel = res.params['center'].value
|
|
186
|
+
center_graph = spl(center_pixel)
|
|
187
|
+
return data_x, data_y, init, fit_x, fit_y, center_graph, center_pixel
|
|
188
|
+
except:
|
|
189
|
+
return None
|
|
190
|
+
|
|
191
|
+
def fit_peak(self, data_x, data_y):
|
|
192
|
+
model = LinearModel() + GaussianModel()
|
|
193
|
+
pars = model.make_params()
|
|
194
|
+
|
|
195
|
+
y1 = data_y[0]
|
|
196
|
+
y2 = data_y[-1]
|
|
197
|
+
x1 = data_x[0]
|
|
198
|
+
x2 = data_x[-1]
|
|
199
|
+
slope = (y2 - y1)/(x2 - x1)
|
|
200
|
+
intercept = y1 - slope*x1
|
|
201
|
+
pars['slope'].value = slope
|
|
202
|
+
pars['intercept'].value = intercept
|
|
203
|
+
center = data_x[data_y.argmax()]
|
|
204
|
+
pars['center'].value = center
|
|
205
|
+
sigma = 5 * abs(data_x[1] - data_x[0])
|
|
206
|
+
pars['sigma'].value = sigma
|
|
207
|
+
height = data_y.max() - (intercept + slope * center)
|
|
208
|
+
pars['amplitude'].value = self.Gauss_amplitude(height, sigma)
|
|
209
|
+
|
|
210
|
+
init = model.eval(pars, x = data_x)
|
|
211
|
+
if self.debug: pars.pretty_print()
|
|
212
|
+
res = model.fit(data_y, pars, x = data_x)
|
|
213
|
+
|
|
214
|
+
if self.debug: print(res.fit_report())
|
|
215
|
+
size = len(self.peaks_data_x)
|
|
216
|
+
fit_x = np.linspace(data_x.min(),data_x.max(),500)
|
|
217
|
+
fit_y = model.eval(res.params, x = fit_x)
|
|
218
|
+
|
|
219
|
+
return data_x, data_y, init, fit_x, fit_y, res
|
|
220
|
+
|
|
221
|
+
def x_2_nm(self, x, i, c1, c2, c3):
|
|
222
|
+
return i +c1*x + c2*x**2 +c3*x**3
|
|
223
|
+
|
|
224
|
+
def Voigt(self, x, c0, c1, c2, c3, amplitude, center, sigma, gamma):
|
|
225
|
+
"""
|
|
226
|
+
Return the Voigt line shape at x with Lorentzian component HWHM gamma
|
|
227
|
+
and Gaussian component sigma.
|
|
228
|
+
sigma = HWHM / sqrt(2 * log(2))
|
|
229
|
+
|
|
230
|
+
"""
|
|
231
|
+
nm = c0 +c1*x + c2*x**2 +c3*x**3
|
|
232
|
+
return amplitude*np.real(wofz((nm - center + 1j*gamma)/sigma/np.sqrt(2))) / sigma /np.sqrt(2*np.pi)
|
|
233
|
+
|
|
234
|
+
def Voigt_amplitude(self, height, gamma, sigma):
|
|
235
|
+
|
|
236
|
+
return height*(sigma*np.sqrt(2*np.pi))/wofz((1j*gamma)/(sigma*np.sqrt(2))).real
|
|
237
|
+
|
|
238
|
+
def Gauss(self, x, c0, c1, c2, c3, amplitude, center, sigma):
|
|
239
|
+
#x pixel
|
|
240
|
+
nm = c0 +c1*x + c2*x**2 +c3*x**3
|
|
241
|
+
cm = 1e7/nm
|
|
242
|
+
center_cm = 1e7/center
|
|
243
|
+
return amplitude / sigma / np.sqrt(2*np.pi) * np.exp( - (cm -center_cm) **2 / 2 / sigma**2 )
|
|
244
|
+
|
|
245
|
+
def Gauss_amplitude(self, height, sigma):
|
|
246
|
+
return sigma * np.sqrt(2*np.pi) * height
|
|
247
|
+
|
|
248
|
+
#
|
|
249
|
+
def statusbar_message(self, message):
|
|
250
|
+
now = datetime.now()
|
|
251
|
+
text = now.strftime("%H:%M:%S : ") + message
|
|
252
|
+
for method in self.statusbar_message_ref:
|
|
253
|
+
method(text)
|
|
254
|
+
|
|
255
|
+
def error_box(self, error):
|
|
256
|
+
msgBox = QtWidgets.QMessageBox()
|
|
257
|
+
msgBox.setIcon(QtWidgets.QMessageBox.Critical)
|
|
258
|
+
msgBox.setWindowTitle("Script Error")
|
|
259
|
+
msgBox.setText(str(error))
|
|
260
|
+
msgBox.setStandardButtons(QtWidgets.QMessageBox.Ok)
|
|
261
|
+
msgBox.exec()
|
|
262
|
+
'''
|
|
263
|
+
#%%
|
|
264
|
+
data_x = np.array((300,400,500,600))
|
|
265
|
+
data_y = np.array((300,400,500,600))
|
|
266
|
+
model = PolynomialModel(degree=2, prefix='line_')
|
|
267
|
+
pars = model.guess(data_y, data_x)
|
|
268
|
+
res = model.fit(data_y, pars, x = data_x)
|
|
269
|
+
pars.pretty_print()
|
|
270
|
+
res.params.pretty_print()
|
|
271
|
+
res.fit_report()
|
|
272
|
+
|
|
273
|
+
Fit = self.model.eval(self.out.params, x = x_fit_lmfit)
|
|
274
|
+
self.center_pk = self.out.params['pk_center'].value
|
|
275
|
+
self.out = self.model.fit(y_fit, self.pars, x = x, max_nfev = self.Fit_iter_lim.get())
|
|
276
|
+
comps = self.out.eval_components(x = x_fit_lmfit)
|
|
277
|
+
'''
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
585.0936329588015, 0.9920106524633822
|
|
2
|
+
588.1179775280899, 0.1238348868175766
|
|
3
|
+
594.3258426966293, 0.23435419440745675
|
|
4
|
+
597.3501872659176, 0.0679094540612517
|
|
5
|
+
602.9213483146068, 0.06924101198402122
|
|
6
|
+
607.059925093633, 0.18375499334221035
|
|
7
|
+
609.2883895131087, 0.2583222370173103
|
|
8
|
+
614.0636704119851, 0.4194407456724367
|
|
9
|
+
616.1329588014981, 0.14647137150466039
|
|
10
|
+
621.3857677902622, 0.118508655126498
|
|
11
|
+
626.3202247191011, 0.2250332889480693
|
|
12
|
+
630.1404494382023, 0.07589880159786955
|
|
13
|
+
632.8464419475656, 0.18242343541944084
|
|
14
|
+
637.7808988764045, 0.2663115845539281
|
|
15
|
+
639.8501872659176, 0.29693741677762975
|
|
16
|
+
650.3558052434457, 0.16644474034620504
|
|
17
|
+
652.9026217228464, 0.07589880159786955
|
|
18
|
+
659.5880149812734, 0.0732356857523303
|
|
19
|
+
667.5468164794008, 0.11584553928095864
|
|
20
|
+
671.5262172284645, 0.1131824234354194
|
|
21
|
+
692.6966292134832, 0.09986684420772307
|
|
22
|
+
703.0430711610487, 0.2809587217043942
|
|
23
|
+
717.368913857678, 0.011984021304926706
|
|
24
|
+
724.5318352059926, 0.08655126498002663
|
|
25
|
+
744.1104868913858, 0.01464713715046595
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
607.43377, 0.18375499334221035
|
|
2
|
+
609.61631, 0.2583222370173103
|
|
3
|
+
614.30626, 0.4194407456724367
|
|
4
|
+
616.35939, 0.14647137150466039
|
|
5
|
+
621.72812, 0.118508655126498
|
|
6
|
+
626.6495, 0.2250332889480693
|
|
7
|
+
630.4789, 0.07589880159786955
|
|
8
|
+
633.44278, 0.18242343541944084
|
|
9
|
+
638.29917, 0.2663115845539281
|
|
10
|
+
640.2246, 0.29693741677762975
|
|
11
|
+
650.65281, 0.16644474034620504
|
|
12
|
+
653.28822, 0.07589880159786955
|
|
13
|
+
659.89529, 0.0732356857523303
|
|
14
|
+
667.82764, 0.11584553928095864
|
|
15
|
+
671.7043, 0.1131824234354194
|
|
16
|
+
692.94673, 0.09986684420772307
|
|
17
|
+
703.24131, 0.2809587217043942
|
|
18
|
+
717.39381, 0.011984021304926706
|
|
19
|
+
724.51666, 0.08655126498002663
|
|
20
|
+
743.8899, 0.01464713715046595
|