%%latex
\tableofcontents
\newpage
__version__ = '2.10.3'
print("JupyLabBook version: %s"%__version__)
print("More info on: %s"%"https://gitlab.com/soleil-data-treatment/soleil-beamlines/soleil-beamline-sirius/JupyLabBook")
#import useful libraries
import numpy as np
import matplotlib.pyplot as plt
from IPython.display import set_matplotlib_formats, Javascript, display
# import custom libraries
import lib.frontend as FE
from lib.extraction.common import PyNexus as PN
from lib.extraction import GIXD
from lib.extraction import GIXS
from lib.extraction import DetectorSum
from lib.extraction import Isotherm
from lib.extraction import Sensors1D
from lib.extraction import XRF
from lib.extraction import XRR
# necessary for plotting in the notebook
%matplotlib inline
# pdf images for the final pdf report
try:
import matplotlib_inline.backend_inline
matplotlib_inline.backend_inline.set_matplotlib_formats('png', 'pdf')
except:
#for IPython<7.23
set_matplotlib_formats('png', 'pdf')
# to have all the cells expanded (not collapsed)
display(Javascript('IPython.OutputArea.prototype._should_scroll = function(lines) {return false;}'))
# define the class experiment
class Experiment:
"""
Class Experiment is used to pass arguments concerning the current experiment only.
"""
def __init__(self):
pass
# test if the expt already exists (avoid loosing info when reloading this cell)
if not 'expt' in locals():
expt = Experiment()
# necessary for saving in pdf
expt.notebook_name = 'Example.ipynb'
# directory where the data will be saved
expt.working_dir = "working/"
# directory where the nexus files are
expt.recording_dir = "recording/"
# directory where the logs are
expt.logs_dir = "logs/"
FE.Action.Check_and_init(expt)
JupyLabBook version: 2.10.3 More info on: https://gitlab.com/soleil-data-treatment/soleil-beamlines/soleil-beamline-sirius/JupyLabBook
Data reduction will be saved in the folder: working/ The original nexus files should be in the folder: recording/ The log files should be in the folder: logs/
$\LARGE \textbf{SIRIUS Beamline}:\textbf{Experiment 1234}$
$\Large \color{red}{\bf Example\ }$
Here we show functions used during beamline alignment.
LaTeX formula can be used in the text:
$$\frac{786-558}{2 \times 2069} \times 0.0355 = 1.9mrad$$
Fit with erf function.
xData, yData, yFit = \
Sensors1D.GaussianRepartitionFit(nxs_filename='SIRIUS_2020_03_11_0744.nxs', recording_dir = expt.recording_dir, \
xLabel='basez', yLabel='camxdeflected', verbose=False)
Fit with Gaussian function.
xData, yData, yFit = \
Sensors1D.GaussianFit(nxs_filename='SIRIUS_2020_03_11_0752.nxs', recording_dir = expt.recording_dir, \
xLabel='delta', yLabel='pilatusroi1', verbose=False)
calib_thetaz_data = np.array([
# gamma channel
[0, 970],
[-1, 899],
[-2, 827],
[-3, 755],
[-4, 683],
[-5, 611],
[-6, 539],
])
expt.thetazfactor=GIXD.Calib_thetaz(calib_thetaz_data)
Extraction of the Yoneda-Vineyard peak.
expt.channel0 = \
GIXD.Extract_channel0(nxs_filename='SIRIUS_2020_03_12_0756.nxs', recording_dir=expt.recording_dir, \
binsize=10, logx=False, logy=False, logz=False, nblevels=50, cmap='jet', \
force_gamma=False, fgamma=0., show_data_stamps = True, verbose=True)
- Open Nexus Data File :
recording/SIRIUS_2020_03_12_0756.nxs
. Number of data points: 101
. Available Counters:
0 -------> delta
1 -------> zs
2 -------> gamma
3 -------> hu36energy
4 -------> xs
5 -------> energydcm
6 -------> current
7 -------> mon2
8 -------> surfacepressure
9 -------> areapermolecule
10 -------> qxy
11 -------> pilatus
12 -------> pilatusroi1
13 -------> integration_time
14 -------> sensorsRelTimestamps
15 -------> sensorsTimestamps
. Pilatus data found, (column 11, alias pilatus)
. qxy data found, (column 10, alias qxy)
. Valid data between points 0 and 100
. Surface pressure data found, mean value 19.74 ± 0.006119 mN/m
. Area per molecule data found, mean value 0.3557 ± 3.944e-05 nm2 per molecule
. Gamma motor data found, mean value -0.0004471 deg
Data not saved. To save data, run a GIXD on the scan. Channel0: 607
x, y, daty, datyTop, datyBottom, datyFirstQuarter, mat, mat_binned, ch_binned, mean_pi, mean_area, mean_gamma = \
GIXD.Treat(nxs_filename='SIRIUS_2020_03_12_0756.nxs', recording_dir=expt.recording_dir, channel0=607.0, \
thetazfactor=0.00024318628377198605, wavelength=0.155, thetac=0.0028, binsize=10, computeqz=True, \
force_gamma=False, fgamma=0.0, absorbers='29 - Vide', logx=False, logy=False, logz=False, \
nblevels=50, cmap='jet', working_dir=expt.working_dir, \
moytocreate=[10, 20, 40], show_data_stamps=True, plot=True, save=True, verbose=True)
- Open Nexus Data File :
recording/SIRIUS_2020_03_12_0756.nxs
. Number of data points: 101
. Available Counters:
0 -------> delta
1 -------> zs
2 -------> gamma
3 -------> hu36energy
4 -------> xs
5 -------> energydcm
6 -------> current
7 -------> mon2
8 -------> surfacepressure
9 -------> areapermolecule
10 -------> qxy
11 -------> pilatus
12 -------> pilatusroi1
13 -------> integration_time
14 -------> sensorsRelTimestamps
15 -------> sensorsTimestamps
. Pilatus data found, (column 11, alias pilatus)
. qxy data found, (column 10, alias qxy)
. Valid data between points 0 and 100
. Surface pressure data found, mean value 19.74 ± 0.006119 mN/m
. Area per molecule data found, mean value 0.3557 ± 3.944e-05 nm2 per molecule
. Gamma motor data found, mean value -0.0004471 deg
Absorbers: 29 - Vide
. Original, non binned, matrix saved in: working/SIRIUS_2020_03_12_0756_1D.mat . Scalar data saved in: working/SIRIUS_2020_03_12_0756_1D.dat . qz values saved in: working/SIRIUS_2020_03_12_0756_1D_qz.dat10 . Binned matrix saved in: working/SIRIUS_2020_03_12_0756_1D.mat10 . XYZ data saved in: working/SIRIUS_2020_03_12_0756_1D.moy10 . qz values saved in: working/SIRIUS_2020_03_12_0756_1D_qz.dat20 . Binned matrix saved in: working/SIRIUS_2020_03_12_0756_1D.mat20 . XYZ data saved in: working/SIRIUS_2020_03_12_0756_1D.moy20 . qz values saved in: working/SIRIUS_2020_03_12_0756_1D_qz.dat40 . Binned matrix saved in: working/SIRIUS_2020_03_12_0756_1D.mat40 . XYZ data saved in: working/SIRIUS_2020_03_12_0756_1D.moy40 . Figure saved in: working/SIRIUS_2020_03_12_0756_1D.pdf
Classic GIXD with: $$q_{xy} = \frac{4\pi}{\lambda}\sin{\left(\frac{2\theta}{2}\right)}$$
Generates:
area, pressure, time = \
Isotherm.Treat(nxs_filename='SIRIUS_Isotherm_2019_02_17_01544.nxs', recording_dir=expt.recording_dir, \
working_dir=expt.working_dir, fast=True, show_data_stamps=False, plot=True, save=True, verbose=False)
Add a 1D plot by clicking on Add plot to report. Generates SIRIUS_2020_03_12_0760.dat
xData, yData = \
Sensors1D.Treat(nxs_filename='SIRIUS_2020_03_12_0760.nxs', recording_dir=expt.recording_dir, \
xLabel='zs', yLabel='camxreflected', working_dir=expt.working_dir, show_data_stamps=False, \
plot=True, save=True, verbose=False)
WAXS on Ag Behenate for calibration. Use the GIXS command with thetai forced to 0.
GIXS: $q_z$ vs $q_{xy}$.
Image and profiles with the approximation $q_{xy} = \frac{4\pi}{\lambda}\sin{\left(\frac{2\theta}{2}\right)}$.
Generates:
images_sum, integrated_qxy, integrated_qz, qxy_array, qz_array = \
GIXS.Treat(nxs_filename='SIRIUS_2021_11_26_6088.nxs', recording_dir=expt.recording_dir, \
wavelength=0.12398, distance=335.5, pixel_PONI_x=572.1, pixel_PONI_y=1016.0, pixel_size=0.172, \
force_gamma=False, force_delta=False, force_thetai=True, fgamma=0.0, fdelta=0.0, fthetai=0.0, \
qxymin=-22.0, qxymax=0.0, qzmin=0.0, qzmax=22.0, \
absorbers='29 - Vide', logz=True, cmap='viridis', working_dir=expt.working_dir, \
show_data_stamps=False, plot=True, save=True, verbose=False)
Absorbers: 29 - Vide gamma found: gamma = -0.9997 deg delta found: delta = -8.875 deg thetai is forced to the value: thetai = 0 deg
GIWAXS on a P3HT film.
images_sum, integrated_qxy, integrated_qz, qxy_array, qz_array = \
GIXS.Treat(nxs_filename='SIRIUS_2021_11_26_6103.nxs', recording_dir=expt.recording_dir, \
wavelength=0.12398, distance=335.5, pixel_PONI_x=572.1, pixel_PONI_y=1016.0, pixel_size=0.172, \
force_gamma=False, force_delta=False, force_thetai=False, fgamma=0.0, fdelta=0.0, fthetai=0.0, \
qxymin=-21.0, qxymax=0.0, qzmin=0.0, qzmax=22.0, \
absorbers='29 - Vide', logz=True, cmap='viridis', working_dir=expt.working_dir, \
show_data_stamps=False, plot=True, save=True, verbose=False)
Absorbers: 29 - Vide gamma found: gamma = -2 deg delta found: delta = -8.875 deg thetai (alphax) found: thetai = 0.1 deg
GISAXS image. Delta and gamma have to be forced to zero (the detector is not on the diffractometer).
images_sum, integrated_qxy, integrated_qz, qxy_array, qz_array = \
GIXS.Treat(nxs_filename='SIRIUS_2021_10_16_2739.nxs', recording_dir=expt.recording_dir, \
wavelength=0.155, distance=4368.9, pixel_PONI_x=490.5, pixel_PONI_y=954.0, pixel_size=0.172, \
force_gamma=True, force_delta=True, force_thetai=False, fgamma=0.0, fdelta=0.0, fthetai=0.0, \
qxymin=-0.65, qxymax=0.65, qzmin=0.0, qzmax=1.3, \
absorbers='', logz=True, cmap='viridis', working_dir=expt.working_dir, \
show_data_stamps=False, plot=True, save=True, verbose=False)
gamma is forced to the value: gamma = 0 deg delta is forced to the value: delta = 0 deg thetai (alphax) found: thetai = 0.18 deg
Plot the sum of the images from a 2D detector. Can also extract and save all the individual images if save='all'.
Here with the Pilatus.
Generates:
images_sum, integrated_x, integrated_y = \
DetectorSum.Treat(nxs_filename='SIRIUS_2021_11_26_6088.nxs', recording_dir=expt.recording_dir, \
xmin=0.0, xmax=980.0, ymin=0.0, ymax=1042.0, \
absorbers='', logz=True, cmap='Greys', working_dir=expt.working_dir, \
show_data_stamps=False, plot=True, save=True, verbose=False)
Works also with the detector UFXC.
images_sum, integrated_x, integrated_y = \
DetectorSum.Treat(nxs_filename='SIRIUS_2021_11_11_3728.nxs', recording_dir=expt.recording_dir, \
xmin=150.0, xmax=170.0, ymin=150.0, ymax=200.0, \
absorbers='', logz=True, cmap='jet', working_dir=expt.working_dir, \
show_data_stamps=True, plot=True, save='all', verbose=False)
. Available Counters:
0 -------> delta
1 -------> shg
2 -------> zs
3 -------> alphax
4 -------> gamma
5 -------> xs
6 -------> energydcm
7 -------> svg
8 -------> current
9 -------> mon2
10 -------> fluoicr00
11 -------> fluoicr01
12 -------> fluoicr02
13 -------> fluoicr03
14 -------> fluospectrum00
15 -------> fluospectrum01
16 -------> fluospectrum02
17 -------> fluospectrum03
18 -------> mon4
19 -------> ionchamber
20 -------> fluoocr00
21 -------> fluoocr01
22 -------> fluoocr02
23 -------> fluoocr03
24 -------> commandfemtoionchamber
25 -------> ufx
26 -------> ufxroi2
27 -------> integration_time
28 -------> sensorsRelTimestamps
29 -------> sensorsTimestamps
Plot XRF from the 4-elements detector, in channels and without peak identification.
Generates:
channels, eVs, spectrums = \
XRF.Treat(nxs_filename='SIRIUS_2017_12_11_08042.nxs', recording_dir=expt.recording_dir, \
list_elems=[0, 1, 2], absorbers='Al 200micron', logz=True, first_channel=100, last_channel=800, use_eV=True, \
gain=10.0, eV0=0.0, arr_peaks=[(None, None)], working_dir=expt.working_dir, fast=True, \
show_data_stamps=False, plot_spectrogram=True, plot_sum=True, plot_first_last=True, save=True, verbose=False)
Absorbers: Al 200micron
Plot XRF from the 1-element detector, in eVs and with peak identification.
Generates:
channels, eVs, spectrums = \
XRF.Treat(nxs_filename='SIRIUS_Fluo_2020_07_03_0042.nxs', recording_dir=expt.recording_dir, \
list_elems=[4], absorbers='Al 800micron', logz=True, first_channel=170, last_channel=1250, use_eV=True, \
gain=9.89, eV0=6.0, arr_peaks=[('Elastic', '12000'), ('Compton', '11670'), ('Cl (Ka1)', '2622'), ('Fe (Ka1)', '6400'), \
('K (Ka1)', '3314')], working_dir=expt.working_dir, fast=True, \
show_data_stamps=False, plot_spectrogram=True, plot_sum=True, plot_first_last=True, save=True, verbose=False)
Absorbers: Al 800micron
To start the calibration click on Calib. XRR.
# For each line of the table:
# 1) Move m4pitch and zs to their suggested values
# 2) Move c10tablepitch and gamma to their suggested value
# 3) Adjust the attenuators
# 4) Align gamma so that the reflection is in the center of the ROI
# 5) Align c10tablepitch and zs around their suggested values
# 6) Replace the values in the table
#
# When done, execute the cell
# Use the value of each fit in the XRR scripts
#
calib_XRR_data = np.array([
# m4pitch c10tablepitch gamma zs
[-0.08, -3335, 5.6, 34.5],
[-0.31, -7935, 3.72396, 16.744],
[-0.54, -12535, 1.84793, -1.012],
[-0.77, -17135, -0.0281093, -18.768],
[-1, -21735, -1.90415, -36.524],
])
expt.distance = 435.5
XRR.Calib(calib_XRR_data, distance=expt.distance)
Select the first scan of the XRR series and click on Plot XRR. Here we show only a few point for the example.
m4pitch, theta, qz, bckg_R_up, bckg_R_down, bckg_R_left, bckg_R_right, bckg_R, err_R, R = \
XRR.Treat(nxs_filename='SIRIUS_2021_04_14_4298.nxs', recording_dir=expt.recording_dir, \
direct_nxs_filename='SIRIUS_2021_04_14_4297.nxs', ROIx0=550, ROIy0=905, ROIsizex=40, ROIsizey=40, \
summation_ROIsizey=7, m4pitch0=-0.0375, wavelength=0.1208, force_direct=False, fdirect=1.0, \
is_bckg_up=True, is_bckg_down=True, is_bckg_left=False, is_bckg_right=False, is_tracking=True, \
working_dir=expt.working_dir, plot_XRR_m4pitch=True, plot_XRR_qz=True, plot_pos_y=True, \
save=True, verbose=False)
Direct extracted from SIRIUS_2021_04_14_4297.nxs: direct=2.44387e+12
Script inserted (with automatic scan numbering) using Insert script.
%shopen
%amove delta -40
%run reset_motors.ipy
%continuous_ascan delta -35 -25 250 5 #123
%tscan 10 10 #124
for i in range(4):
%amove delta -20
%continuous_ascan delta -10 -3 175 5 #125 #127 #129 #131
%run reset_motors.ipy
%run cont_regh_abs.ipy #126 #128 #130 #132
for i in range(3):
%amove delta -20
%dscan delta -10 -3 175 5 #133 #135 #137
%run reset_motors.ipy
#%run cont_regh_abs.ipy
%run cont_regh_abs.ipy #134 #136 #138
for i in range(2):
%amove delta -20
%tscan 10 100 #139 #140
%slist scan add camxdirect
%continuous_ascan delta -35 -25 250 5 #141
# %tscan 10 10
%shclose
Positions extracted from the logs, using Insert positions.
| alphax | gamma |
|---|---|
| 2.0679 | 4.1401 |
| deltacodeur | euchi | euth | euphi | kappa_h | kappa_k |
|---|---|---|---|---|---|
| 1.00196 | -89.57961 | 90.42039 | -0.00580 | -0.08252 | |
| Degrees | deg | deg | deg |
| kappa_l | qxy | qxy0 | qz | basexPoint | basexTrait |
|---|---|---|---|---|---|
| -0.18486 | 2.0556 | 23.82 | -0.92 | -15.7275 | -15.7274 |
| nm-1 | nm-1 | nm-1 |
| basezPlan | basezPoint | basezTrait | basepitch | baseroll | basex |
|---|---|---|---|---|---|
| 71.1257 | 71.1257 | 71.1257 | -0.0000 | 0.000 | -15.727 |
| mrad | mrad | mm |
| baseyaw | basez | alphax | alphay | delta | delta0 |
|---|---|---|---|---|---|
| -0.000 | 71.126 | 0.2998 | 0.2000 | -2.9110 | -34.2322 |
| mrad | mm |
| deltaa | etaa | gamma | kappav | mu | kphi |
|---|---|---|---|---|---|
| 0.0000 | 0.0000 | 1.2997 | 1.3080 | -179.9997 | 0.0000 |
| thetaa | thetah | komega | xs | ky | ys |
|---|---|---|---|---|---|
| 0.0000 | 0.0185 | 0.0000 | 0.0000 | -0.1000 | 0.0000 |
| kz | zs | kx |
|---|---|---|
| 0.0000 | -41.9999 | -0.1000 |
Commands extracted from the logs, using Insert commands.
Fri, 26 Nov 2021 14:13:34 ct 1 pilatus
Fri, 26 Nov 2021 14:13:56 tscan 10 10 #6109
Fri, 26 Nov 2021 14:17:29 shclose
Fri, 26 Nov 2021 14:26:40 run config_alignment.ipy
Fri, 26 Nov 2021 10:34:48 ct 1 pilatus
Human-readable logs generated in the folder /working/readable_logs/ by clicking on Convert logs.
Using the command Insert image.

Save the current state of the notebook (the variable expt) by clicking on Save state.
import pickle
with open('working/expt.pkl', 'wb') as f:
pickle.dump(expt, f, pickle.HIGHEST_PROTOCOL)
Load the previous state of the notebook by clicking on Load state(for example after creating a new notebook).
import pickle
with open('working/expt.pkl', 'rb') as f:
expt = pickle.load(f)
Use the button Insert text to insert text into the report.
PDF generated by clicking on Export to pdf.
FE.Action.Choose(expt)
Export in progress...
Notebook exported to Example.pdf