The aim of this document is to explain how to use pyFAI.goniometer for calibrating the position of the detector from the goniometer encoders.
Those data have been acquired at ROBL (ESRF-BM20 German CRG) in winter 2017 by Christoph Henning using a Pilatus 100k detector and LaB6 as calibrant. One hundred and twenty one images have been acquired with the detector moving between 5 and 65 degree with a step size of half a degree. The motor position is registered in the filename.
A prior manual calibration (using pyFAI-calib) has been performed on four images locate at 31.5, 33.5, 35 and 35.5 degrees. Those images were the first with two rings. The control points extrated during this initial calibration has been used as a starting point for this calibration. Then more images have been added to make the model more robust.
The raw data files are available at: http://www.silx.org/pub/pyFAI/gonio/Pilatus-100k-LaB6/
Initialization of the plotting library, matplotlib, to be used with the jupyter notebook
%pylab nbagg
import time
start_time = time.time()
Populating the interactive namespace from numpy and matplotlib
#Download all images
import os
from silx.resources import ExternalResources
#Specific for ESRF
os.environ["http_proxy"] = "http://proxy.esrf.fr:3128"
downloader = ExternalResources("pyFAI", "http://www.silx.org/pub/pyFAI/testimages", "PYFAI_DATA")
all_files = downloader.getdir("LaB6_gonio_BM20.tar.bz2")
print(all_files)
['/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_45.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_08.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_20.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/minimum-mask.edf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_09.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_53.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_60.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_63.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_56.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_12.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_53.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_42.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_16.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_05.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_47.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_39.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_47.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_57.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_35.5_0001p.poni', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_07.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_41.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_51.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_33.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_22.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_43.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_64.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_35.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_13.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_08.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_29.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_45.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_63.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_61.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_31.5_0001p.npt', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_11.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_46.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_11.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_56.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_18.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_06.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_46.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_58.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_35.5_0001p.npt', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_30.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_15.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_36.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_13.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_55.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_27.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_31.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_24.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_38.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_48.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_16.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_52.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_38.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_54.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_48.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_31.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_28.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_21.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_06.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_25.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_40.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_44.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_39.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_35.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_62.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_36.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_57.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_28.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_17.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_24.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_35.0_0001p.poni', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_50.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_18.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_27.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_19.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_21.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_17.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_50.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_44.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_30.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_51.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_62.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_05.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_26.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_31.5_0001p.poni', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_23.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_33.5_0001p.poni', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_37.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_19.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_29.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_10.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_40.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_58.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_49.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_09.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_15.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_43.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_60.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_34.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_20.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/deviation-mask.edf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_41.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_07.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_54.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_33.5_0001p.npt', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_33.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_32.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_59.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_14.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_32.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_59.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_65.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_25.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_61.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_34.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_52.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_22.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_10.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_42.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_64.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_14.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_26.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_49.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_35.0_0001p.npt', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_55.5_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_23.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_12.0_0001p.cbf', '/tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_37.0_0001p.cbf']
#Loading of a few libraries
import os
import random
import fabio
import pyFAI
from pyFAI.goniometer import GeometryTransformation, GoniometerRefinement, Goniometer
from pyFAI.gui import jupyter
#loading of the list of files, and display of the last one with its headers
image_files = [i for i in all_files if i.endswith(".cbf")]
image_files.sort()
print("List of images: " + ", ".join(image_files) + "." + os.linesep)
fimg = fabio.open(image_files[-1])
print("Image headers:")
for key, value in fimg.header.items():
print("%s: %s"%(key,value))
jupyter.display(fimg.data, label=os.path.basename(fimg.filename))
List of images: /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_05.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_05.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_06.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_06.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_07.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_07.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_08.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_08.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_09.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_09.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_10.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_10.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_11.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_11.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_12.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_12.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_13.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_13.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_14.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_14.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_15.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_15.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_16.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_16.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_17.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_17.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_18.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_18.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_19.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_19.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_20.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_20.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_21.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_21.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_22.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_22.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_23.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_23.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_24.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_24.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_25.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_25.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_26.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_26.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_27.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_27.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_28.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_28.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_29.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_29.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_30.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_30.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_31.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_31.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_32.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_32.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_33.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_33.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_34.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_34.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_35.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_35.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_36.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_36.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_37.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_37.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_38.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_38.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_39.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_39.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_40.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_40.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_41.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_41.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_42.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_42.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_43.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_43.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_44.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_44.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_45.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_45.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_46.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_46.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_47.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_47.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_48.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_48.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_49.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_49.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_50.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_50.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_51.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_51.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_52.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_52.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_53.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_53.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_54.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_54.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_55.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_55.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_56.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_56.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_57.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_57.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_58.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_58.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_59.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_59.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_60.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_60.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_61.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_61.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_62.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_62.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_63.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_63.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_64.0_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_64.5_0001p.cbf, /tmp/pyFAI_testdata_kieffer/LaB6_gonio_BM20/del_65.0_0001p.cbf.
Image headers:
_array_data.header_convention: PILATUS_1.2
_array_data.header_contents: # Detector: PILATUS 2M, 24-0111
# 2016-05-17T18:12:57.232113
# Pixel_size 172e-6 m x 172e-6 m
# Silicon sensor, thickness 0.000450 m
# Exposure_time 9.9977 s
# Exposure_period 9.9977 s
# Tau = 1.991e-07 s
# Count_cutoff 1071182 counts
# Threshold_setting: 4024.0 eV
# Gain_setting: low gain (vrf = -0.300)
# N_excluded_pixels = 1
# Excluded_pixels: badpix_mask.tif
# Flat_field: FF_p2m0111_E26000_T13000_vrf_m0p30.tif
# Trim_file: p2m0111_E26000_T13000_vrf_m0p30.bin
# Image_path: /ramdisk/
# Wavelength 0.7749 A
# Start_angle 0.00 deg.
# Angle_increment 0.00 deg.
# Omega 0.00 deg.
# Omega_increment 0.00 deg.
# Phi 0.00 deg.
# Phi_increment 0.00 deg.
# Kappa 0.0 deg.
# Oscillation_axis PHI
# Detector_distance 0.157 m
# Detector_Voffset 0.0 m
# Beam_xy (542.41, 732.4) pixels
# Flux 0 counts
# Temperature 0.00 K
# Blower 0.0 C
# Lakeshore 0.00 K
Content-Type: application/octet-stream;
conversions: x-CBF_BYTE_OFFSET
Content-Transfer-Encoding: BINARY
X-Binary-Size: 95035
X-Binary-ID: 1
X-Binary-Element-Type: signed 32-bit integer
X-Binary-Element-Byte-Order: LITTLE_ENDIAN
Content-MD5: darooj/7FEQRNdNzNDo0XQ==
X-Binary-Number-of-Elements: 94965
X-Binary-Size-Fastest-Dimension: 487
X-Binary-Size-Second-Dimension: 195
X-Binary-Size-Padding: 4095
<IPython.core.display.Javascript object>
<matplotlib.axes._subplots.AxesSubplot at 0x7ffb27d85a90>
This is the most difficult part to understand.
The next cell defines 2 functions, one for transforming the geometry and the other one to read the goniometer angle from the metadata
#Definition of the goniometer translation function:
# The detector rotates vertically, around the horizontal axis, i.e. rot2
goniotrans = GeometryTransformation(param_names = ["dist", "poni1", "poni2", "rot1",
"rot2_offset", "rot2_scale"],
dist_expr="dist",
poni1_expr="poni1",
poni2_expr="poni2",
rot1_expr="rot1",
rot2_expr="rot2_scale * pos + rot2_offset",
rot3_expr="0.0")
#Definition of the function reading the goniometer angle from the filename of the image.
def get_angle(basename):
"""Takes the basename (like del_65.0_0001p ) and returns the angle of the detector"""
return float(os.path.basename((basename.split("_")[1])))
basename = os.path.basename(fimg.filename)
print('filename', basename, "angle:",get_angle(basename))
filename del_65.0_0001p.cbf angle: 65.0
#Definition of the detector, its mask, the calibrant
mask_files = [i for i in all_files if i.endswith("-mask.edf")]
mask = numpy.logical_or(fabio.open(mask_files[0]).data, fabio.open(mask_files[1]).data)
pilatus = pyFAI.detector_factory("Pilatus100k")
pilatus.mask = mask
LaB6 = pyFAI.calibrant.CALIBRANT_FACTORY("LaB6")
wavelength = 7.7490120575e-11
LaB6.wavelength = wavelength
#Definition of the geometry refinement: the parameter order is the same as the param_names
param = {"dist":0.8,
"poni1":0.02,
"poni2":0.04,
"rot1":0,
"rot2_offset":0,
"rot2_scale": numpy.pi/180. # rot2 is in radians, while the motor position is in degrees
}
#Defines the bounds for some variables
bounds = {"dist": (0.79, 0.81),
"rot1": (-0.01, 0.01),
"rot2_offset": (-0.01, 0.01),
"rot2_scale": (numpy.pi/180., numpy.pi/180.) #strict bounds on the scale: we expect the gonio to be precise
}
gonioref = GoniometerRefinement(param, #initial guess
bounds=bounds,
pos_function=get_angle,
trans_function=goniotrans,
detector=pilatus, wavelength=wavelength)
print("Empty refinement object:")
print(gonioref)
Empty refinement object:
GoniometerRefinement with 0 geometries labeled: .
#Let's populate the goniometer refinement object with all control point files:
ponis = [i for i in all_files if i.endswith(".poni")]
ponis.sort()
for fn in ponis:
base = os.path.splitext(fn)[0]
basename = os.path.basename(base)
fimg = fabio.open(base + ".cbf")
sg =gonioref.new_geometry(basename, image=fimg.data, metadata=basename, control_points=base+".npt",
geometry=fn, calibrant=LaB6)
print(sg.label, "Angle:", sg.get_position())
print(sg.geometry_refinement)
print()
print("Filled refinement object:")
print(gonioref)
del_31.5_0001p Angle: 31.5
Detector Pilatus 100k PixelSize= 1.720e-04, 1.720e-04 m
Wavelength= 7.749012e-11m
SampleDetDist= 8.058209e-01m PONI= 5.700310e-03, 4.599931e-02m rot1=-0.000000 rot2= 0.560707 rot3= -0.000065 rad
DirectBeamDist= 951.518mm Center: x=267.438, y=2975.017 pix Tilt=32.126 deg tiltPlanRotation= 90.000 deg
del_33.5_0001p Angle: 33.5
Detector Pilatus 100k PixelSize= 1.720e-04, 1.720e-04 m
Wavelength= 7.749012e-11m
SampleDetDist= 8.061475e-01m PONI= 1.998418e-02, 4.623309e-02m rot1=0.000061 rot2= 0.577898 rot3= -0.000000 rad
DirectBeamDist= 962.435mm Center: x=268.511, y=3172.837 pix Tilt=33.111 deg tiltPlanRotation= 90.005 deg
del_35.0_0001p Angle: 35.0
Detector Pilatus 100k PixelSize= 1.720e-04, 1.720e-04 m
Wavelength= 7.749012e-11m
SampleDetDist= 8.053432e-01m PONI= 5.551240e-03, 4.624546e-02m rot1=-0.000016 rot2= 0.622009 rot3= 0.000012 rad
DirectBeamDist= 990.936mm Center: x=268.944, y=3389.181 pix Tilt=35.638 deg tiltPlanRotation= 89.999 deg
del_35.5_0001p Angle: 35.5
Detector Pilatus 100k PixelSize= 1.720e-04, 1.720e-04 m
Wavelength= 7.749012e-11m
SampleDetDist= 8.061272e-01m PONI= 5.998339e-03, 3.450065e-02m rot1=-0.014779 rot2= 0.630136 rot3= 0.000007 rad
DirectBeamDist= 997.856mm Center: x=269.857, y=3453.432 pix Tilt=36.113 deg tiltPlanRotation= 88.839 deg
Filled refinement object:
GoniometerRefinement with 4 geometries labeled: del_31.5_0001p, del_33.5_0001p, del_35.0_0001p, del_35.5_0001p.
#Display all images with associated calibration:
for sg in gonioref.single_geometries.values():
jupyter.display(sg=sg)
<IPython.core.display.Javascript object>
<IPython.core.display.Javascript object>
<IPython.core.display.Javascript object>
<IPython.core.display.Javascript object>
# Initial refinement of the goniometer model with 5 dof
gonioref.refine2()
Cost function before refinement: 4.67628027948e-05
fun: 3.474545890145023e-09
jac: array([ 1.55798008e-08, 6.20442923e-08, -8.86840831e-09,
9.38196637e-09, 4.54171855e-08, 5.30002449e-06])
message: 'Optimization terminated successfully.'
nfev: 145
nit: 18
njev: 18
status: 0
success: True
x: array([ 0.80587963, 0.01626972, 0.04374852, -0.00299843, -0.00217847,
0.01745329])
Cost function after refinement: 3.474545890145023e-09
GonioParam(dist=0.80587963251952144, poni1=0.016269720064575065, poni2=0.04374852465218073, rot1=-0.0029984302141578345, rot2_offset=-0.0021784698875247318, rot2_scale=0.017453292519943295)
maxdelta on: dist (0) 0.8 --> 0.80587963252
array([ 0.80587963, 0.01626972, 0.04374852, -0.00299843, -0.00217847,
0.01745329])
# This function adds new images to the pool of data used for the refinement.
# A set of new control points are extractred and a refinement step is performed at each iteration
# The last image of the serie is displayed
def optimize_with_new_images(list_images, pts_per_deg=1):
sg = None
for fname in list_images:
print()
basename = os.path.basename(fname)
base = os.path.splitext(basename)[0]
fimg = fabio.open(fname)
if base in gonioref.single_geometries:
continue
print(base)
sg = gonioref.new_geometry(base, image=fimg.data, metadata=base,
calibrant=LaB6)
print(sg.extract_cp(pts_per_deg=pts_per_deg))
print("*"*50)
gonioref.refine2()
if sg:
sg.geometry_refinement.set_param(gonioref.get_ai(sg.get_position()).param)
jupyter.display(sg=sg)
# Append all other images bewteen 30 and 40 degrees
images_30_40 = [i for i in all_files if ("del_3" in i and i.endswith("0001p.cbf"))]
random.shuffle(images_30_40)
optimize_with_new_images(images_30_40, pts_per_deg=3)
del_30.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: # c ring 6: 36 points del_38.5_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: # d ring 10: 30 points # e ring 11: 30 points del_37.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: # f ring 10: 30 points del_36.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: # g ring 9: 36 points del_32.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: # h ring 7: 36 points del_37.0_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: # i ring 9: 36 points # j ring 10: 30 points del_38.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: # k ring 10: 30 points del_32.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: # l ring 7: 36 points del_34.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: # m ring 8: 36 points del_36.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: # n ring 9: 36 points del_39.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: # o ring 11: 30 points del_30.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: # p ring 6: 36 points del_33.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: # q ring 7: 36 points del_39.0_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: # r ring 10: 15 points # s ring 11: 30 points del_31.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: # t ring 6: 36 points del_34.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: # u ring 8: 36 points ********************************************** Cost function before refinement: 3.78586503256e-09 fun: 3.785478428600372e-09 jac: array([ 2.02798652e-08, -1.40537854e-06, -4.03506535e-07, 3.25207815e-07, -1.13637203e-06, -7.90020799e-05]) message: 'Optimization terminated successfully.' nfev: 10 nit: 1 njev: 1 status: 0 success: True x: array([ 0.80587963, 0.01627002, 0.04374861, -0.0029985 , -0.00217823, 0.01745329]) Cost function after refinement: 3.785478428600372e-09 GonioParam(dist=0.80587962817888781, poni1=0.016270020867037542, poni2=0.043748611017352793, rot1=-0.0029984998205369322, rot2_offset=-0.0021782266623036049, rot2_scale=0.017453292519943295) maxdelta on: poni1 (1) 0.0162697200646 --> 0.016270020867
<IPython.core.display.Javascript object>
# Append all other images
all_images = [i for i in all_files if i.endswith(".cbf")]
random.shuffle(all_images)
optimize_with_new_images(all_images)
del_44.5_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: # v ring 13: 10 points # w ring 14: 10 points del_54.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: # x ring 20: 8 points del_11.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: # y ring 0: 32 points del_15.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: # z ring 1: 24 points del_59.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #aa ring 23: 6 points del_05.5_0001p ControlPoints instance containing 0 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 0 groups of points: del_42.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #ab ring 12: 10 points del_25.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #ac ring 5: 14 points del_14.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #ad ring 1: 24 points del_51.5_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #ae ring 18: 7 points #af ring 19: 8 points del_53.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #ag ring 20: 8 points del_14.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #ah ring 1: 10 points del_17.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #ai ring 2: 10 points del_10.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #aj ring 0: 34 points del_22.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #ak ring 3: 17 points del_25.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #al ring 4: 16 points del_10.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #am ring 0: 26 points del_23.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #an ring 4: 16 points del_62.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #ao ring 25: 8 points del_21.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #ap ring 3: 17 points del_42.5_0001p ControlPoints instance containing 0 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 0 groups of points: del_47.0_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #aq ring 15: 10 points #ar ring 16: 9 points del_41.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #as ring 12: 10 points del_18.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #at ring 2: 19 points del_64.5_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #au ring 26: 8 points #av ring 27: 8 points del_09.0_0001p ControlPoints instance containing 0 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 0 groups of points: del_20.0_0001p ControlPoints instance containing 0 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 0 groups of points: del_58.0_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #aw ring 22: 7 points #ax ring 23: 8 points del_54.5_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #ay ring 20: 8 points #az ring 21: 3 points del_47.5_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #ba ring 15: 10 points #bb ring 16: 9 points del_29.0_0001p ControlPoints instance containing 0 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 0 groups of points: del_55.5_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #bc ring 20: 8 points #bd ring 21: 8 points del_57.5_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #be ring 22: 7 points #bf ring 23: 7 points del_13.5_0001p ControlPoints instance containing 0 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 0 groups of points: del_29.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #bg ring 6: 7 points del_12.5_0001p ControlPoints instance containing 0 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 0 groups of points: del_51.0_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #bh ring 18: 8 points #bi ring 19: 8 points del_46.5_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #bj ring 14: 7 points #bk ring 15: 10 points del_06.5_0001p ControlPoints instance containing 0 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 0 groups of points: del_59.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #bl ring 24: 8 points del_26.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #bm ring 5: 14 points del_43.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #bn ring 13: 10 points del_16.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #bo ring 1: 24 points del_22.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #bp ring 3: 17 points del_20.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #bq ring 3: 17 points del_57.0_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #br ring 22: 8 points #bs ring 23: 8 points del_56.5_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #bt ring 21: 8 points #bu ring 22: 8 points del_07.0_0001p ControlPoints instance containing 0 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 0 groups of points: del_52.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #bv ring 19: 8 points del_21.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #bw ring 3: 17 points del_40.5_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #bx ring 11: 10 points #by ring 12: 10 points del_43.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #bz ring 13: 10 points del_55.0_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #ca ring 20: 8 points #cb ring 21: 8 points del_06.0_0001p ControlPoints instance containing 0 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 0 groups of points: del_13.0_0001p ControlPoints instance containing 0 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 0 groups of points: del_27.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #cc ring 5: 14 points del_61.5_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #cd ring 24: 8 points #ce ring 25: 8 points del_28.0_0001p ControlPoints instance containing 0 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 0 groups of points: del_49.5_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #cf ring 17: 9 points #cg ring 18: 3 points del_26.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #ch ring 5: 14 points del_63.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #ci ring 26: 8 points del_24.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #cj ring 4: 16 points del_17.0_0001p ControlPoints instance containing 0 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 0 groups of points: del_07.5_0001p ControlPoints instance containing 0 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 0 groups of points: del_65.0_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #ck ring 27: 7 points #cl ring 28: 8 points del_48.5_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #cm ring 16: 9 points #cn ring 17: 9 points del_18.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #co ring 2: 19 points del_19.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #cp ring 2: 19 points del_45.5_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #cq ring 14: 10 points #cr ring 15: 2 points del_61.0_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #cs ring 24: 8 points #ct ring 25: 8 points del_53.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #cu ring 19: 8 points del_60.5_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #cv ring 24: 8 points #cw ring 25: 8 points del_24.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #cx ring 4: 16 points del_05.0_0001p ControlPoints instance containing 0 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 0 groups of points: del_40.0_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #cy ring 11: 9 points #cz ring 12: 10 points del_48.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #da ring 16: 9 points del_28.5_0001p ControlPoints instance containing 0 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 0 groups of points: del_08.0_0001p ControlPoints instance containing 0 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 0 groups of points: del_09.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #db ring 0: 14 points del_08.5_0001p ControlPoints instance containing 0 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 0 groups of points: del_41.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #dc ring 12: 10 points del_64.0_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #dd ring 26: 8 points #de ring 27: 8 points del_45.0_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #df ring 13: 10 points #dg ring 14: 10 points del_15.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #dh ring 1: 24 points del_63.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #di ring 26: 8 points del_12.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #dj ring 0: 11 points del_56.0_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #dk ring 21: 8 points #dl ring 22: 8 points del_62.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #dm ring 25: 8 points del_52.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #dn ring 19: 8 points del_27.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #do ring 5: 14 points del_44.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #dp ring 13: 10 points del_50.5_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #dq ring 17: 9 points #dr ring 18: 8 points del_19.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #ds ring 2: 19 points del_50.0_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #dt ring 17: 9 points #du ring 18: 8 points del_23.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #dv ring 4: 11 points del_60.0_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #dw ring 24: 8 points del_46.0_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #dx ring 14: 10 points #dy ring 15: 10 points del_11.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #dz ring 0: 30 points del_16.5_0001p ControlPoints instance containing 0 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 0 groups of points: del_58.5_0001p ControlPoints instance containing 1 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 1 groups of points: #ea ring 23: 8 points del_49.0_0001p ControlPoints instance containing 2 group of point: LaB6 Calibrant with 97 reflections at wavelength 7.7490120575e-11 Containing 2 groups of points: #eb ring 16: 9 points #ec ring 17: 9 points ********************************************** Cost function before refinement: 1.5418692807e-08 fun: 1.2653965346381429e-08 jac: array([ -7.40160115e-08, 8.08276352e-07, -1.43417888e-08, 5.60775004e-09, 6.52925588e-07, -1.01581876e-03]) message: 'Optimization terminated successfully.' nfev: 49 nit: 6 njev: 6 status: 0 success: True x: array([ 0.80588628, 0.01627363, 0.043281 , -0.00262053, -0.002175 , 0.01745329]) Cost function after refinement: 1.2653965346381429e-08 GonioParam(dist=0.80588628202624024, poni1=0.016273634721444413, poni2=0.043280998683283237, rot1=-0.0026205297731339019, rot2_offset=-0.0021749982834775843, rot2_scale=0.017453292519943295) maxdelta on: poni2 (2) 0.0437486110174 --> 0.0432809986833
<IPython.core.display.Javascript object>
# Check the calibration of the first and the last image with rings
print("First & last rings")
print("Total number of images:", len(gonioref.single_geometries) )
fig = plt.figure()
for idx,lbl in enumerate(["del_10.0_0001p", "del_65.0_0001p"]):
sg = gonioref.single_geometries[lbl]
if sg.control_points.get_labels():
sg.geometry_refinement.set_param(gonioref.get_ai(sg.get_position()).param)
jupyter.display(sg=sg, ax=fig.add_subplot(2, 1, idx+1))
First & last rings
Total number of images: 121
<IPython.core.display.Javascript object>
# Final pass of refinement with all constrains removed, very fine refinement
gonioref.bounds = None
gonioref.refine2("slsqp", eps=1e-13, maxiter=10000, ftol=1e-12)
Cost function before refinement: 1.26539653464e-08
fun: 1.1079685608729184e-08
jac: array([ 5.21785530e-08, 1.26889506e-08, 5.26831332e-07,
-4.24227849e-07, 1.14978105e-08, 1.42936810e-08])
message: 'Optimization terminated successfully.'
nfev: 36
nit: 4
njev: 4
status: 0
success: True
x: array([ 0.8058864 , 0.01622186, 0.04328034, -0.00261997, -0.00221674,
0.01745626])
Cost function after refinement: 1.1079685608729184e-08
GonioParam(dist=0.80588640493195618, poni1=0.016221864667863021, poni2=0.043280336616327734, rot1=-0.0026199663308397385, rot2_offset=-0.0022167400134821824, rot2_scale=0.017456261552178831)
maxdelta on: poni1 (1) 0.0162736347214 --> 0.0162218646679
array([ 0.8058864 , 0.01622186, 0.04328034, -0.00261997, -0.00221674,
0.01745626])
#Create a MultiGeometry integrator from the refined geometry:
angles = []
images = []
for sg in gonioref.single_geometries.values():
angles.append(sg.get_position())
images.append(sg.image)
multigeo = gonioref.get_mg(angles)
multigeo.radial_range=(3, 68)
print(multigeo)
MultiGeometry integrator with 121 geometries on (3, 68) radial range (2th_deg) and (-180, 180) azimuthal range (deg)
# Integrate the whole set of images in a single run:
res = multigeo.integrate1d(images, 10000)
jupyter.plot1d(res)
<IPython.core.display.Javascript object>
<matplotlib.axes._subplots.AxesSubplot at 0x7ffad1ff95f8>
# Save the goniometer configuration with 1 angle
gonioref.save("ROBL_v1.json")
#Can the refinement be improved by freeing another degree of freedom ? what about rot1 ?
goniotrans2 = GeometryTransformation(param_names = ["dist", "poni1", "poni2",
"rot1", "rot1_scale",
"rot2_offset", "rot2_scale"],
dist_expr="dist",
poni1_expr="poni1",
poni2_expr="poni2",
rot1_expr="rot1_scale * pos + rot1",
rot2_expr="rot2_scale * pos + rot2_offset",
rot3_expr="0.0")
param2 = (gonioref.nt_param(*gonioref.param))._asdict()
param2["rot1_scale"] = 0
gonioref2 = GoniometerRefinement(param2,
pos_function = get_angle,
trans_function=goniotrans2,
detector=pilatus,
wavelength=wavelength)
gonioref2.single_geometries = gonioref.single_geometries.copy()
print(gonioref2.chi2(), gonioref.chi2())
gonioref2.refine2()
gonioref2.save("ROBL_v2.json")
1.10796856087e-08 1.10796856087e-08
Cost function before refinement: 1.10796856087e-08
fun: 4.754350840871057e-09
jac: array([ 5.35082313e-08, -1.10894246e-07, -5.29857408e-09,
4.75679152e-09, 1.68307757e-08, -9.27227720e-08,
-3.88850517e-06])
message: 'Optimization terminated successfully.'
nfev: 121
nit: 13
njev: 13
status: 0
success: True
x: array([ 8.05873589e-01, 1.62083546e-02, 4.17665409e-02,
-1.39612789e-03, -1.28555852e-04, -2.22689562e-03,
1.74566332e-02])
Cost function after refinement: 4.754350840871057e-09
GonioParam(dist=0.80587358868352343, poni1=0.016208354569446009, poni2=0.041766540922984097, rot1=-0.0013961278865829037, rot1_scale=-0.00012855585206377195, rot2_offset=-0.0022268956160008172, rot2_scale=0.017456633219776127)
maxdelta on: poni2 (2) 0.0432803366163 --> 0.041766540923
# Check the calibration of the first and the last image with rings
print("First & last rings")
fig = plt.figure()
for idx,lbl in enumerate(["del_10.0_0001p", "del_65.0_0001p"]):
sg = gonioref.single_geometries[lbl]
if sg.control_points.get_labels():
sg.geometry_refinement.set_param(gonioref2.get_ai(sg.get_position()).param)
jupyter.display(sg=sg, ax=fig.add_subplot(2, 1, idx+1))
First & last rings
<IPython.core.display.Javascript object>
#Create a MultiGeometry integrator from the refined geometry and display the integrated image:
multigeo2 = gonioref2.get_mg(angles)
multigeo2.radial_range=(3, 68)
print(multigeo2)
res2 = multigeo2.integrate1d(images, 10000)
#Display the 2 curves with a zoom
fig = figure(figsize=(10,5))
ax = fig.add_subplot(1,2,1)
ax.plot(*res2, label="rot1 & rot2 rotation")
ax.plot(*res, label="rot2 only rotation")
ax.set_xlabel(res.unit.label)
ax.set_ylabel("Intensity")
ax.set_title("Azimuthal integration of 121 images merged")
ax.legend()
ay = fig.add_subplot(1,2,2)
ay.plot(*res2, label="rot1 & rot2 rotation")
ay.plot(*res, label="rot2 only rotation")
ay.set_xlabel(res.unit.label)
ay.set_ylabel("Intensity")
ay.set_xlim(10.5,11)
ay.set_title("Zoom on first peak")
ay.legend()
MultiGeometry integrator with 121 geometries on (3, 68) radial range (2th_deg) and (-180, 180) azimuthal range (deg)
<IPython.core.display.Javascript object>
<matplotlib.legend.Legend at 0x7ffad1b43cf8>
print("Total execution time: %.3fs"%(time.time() - start_time))
Total execution time: 33.339s
With the first model, the refinement was not perfect on the very low angles and indicates a miss-fit. Relaxing the constrains on rot1 allowed to spot a non (perfect) orthogonality between the goniometer axis and the incident beam. Releasing the distances is also possible, for example to cope with the sample not perfectly mounted on the center of the goniometer.
This notebook exposes the how to calibrate the goniometer for a small detector moving on a 2theta arm. Once calibrated, the geometry can be saved and restored and stays valid as long as the detector or the goniometer is not unmounted from the beam-line. This configuration can subsequently be used to integrate the data acquired with any sample, in minutes instead of hours. The resolution limit is now the pixel size. Fortunately, pixel detector with small pixel like the MaxiPix or the Lambda detector exists and offer higher resolution.