Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
49 commits
Select commit Hold shift + click to select a range
ebc920c
Add polarised experiment [ci skip]
wardsimon Apr 6, 2020
1d1ce31
Add chi2 options
wardsimon Apr 6, 2020
991fa5f
Calculate profile up/down
wardsimon Apr 6, 2020
b8e76f2
RE-implement chi2
wardsimon Apr 7, 2020
67df908
Add Polarization efficiency/level [ci skip]
wardsimon Apr 7, 2020
130e2f3
Fix fitable values
wardsimon Apr 7, 2020
613e503
Fix hidden refinement [ci skip]
wardsimon Apr 7, 2020
16e8d6b
Remove auto-refine [ci skip]
wardsimon Apr 7, 2020
d08c43c
Temporary fix of min/max for polarization and efficiency
AndrewSazonov Apr 8, 2020
2f1974d
Fix calculated pattern values
AndrewSazonov Apr 15, 2020
1859313
Add calculated background
AndrewSazonov Apr 15, 2020
88c16d1
Fix background for polarised neutrons
AndrewSazonov Apr 15, 2020
23a5f27
Fixup creation of phaess and exps [ci skip]
wardsimon Apr 16, 2020
102f0c8
Typo fixes [ci skip]
wardsimon Apr 17, 2020
be3679f
Fix polarisation (until cryspy is fixed)
wardsimon Apr 21, 2020
e2c08a6
Fix refine polarisation
wardsimon Apr 21, 2020
56e64e1
Fix error on scale
wardsimon Apr 21, 2020
2787feb
Don't print to the console
AndrewSazonov Apr 21, 2020
fe053a0
Create empty cryspy obj if rcif path is None
AndrewSazonov Apr 22, 2020
d26a9d9
Fix experiments as cif
wardsimon Apr 24, 2020
4fae732
1st implementation of editable CIF at the back end
AndrewSazonov Apr 29, 2020
0be59bf
Fix issue with complex numbers for the scattering length
AndrewSazonov Apr 30, 2020
b98b7f4
Change space group name source
AndrewSazonov May 1, 2020
394c28c
Add exp from cif compatibility
wardsimon May 6, 2020
372c2f8
Add phase from cif compatibility
wardsimon May 6, 2020
ea9b9f9
Allow to run bulk update without macro
AndrewSazonov May 6, 2020
361c32c
Add datablock label to calculations cif
AndrewSazonov May 7, 2020
efc6785
Part of back-end implementation of Main.cif Edit
AndrewSazonov May 7, 2020
b353469
Remove global_ from CIFs on saving
AndrewSazonov May 7, 2020
5ca0905
Simplify writing CIF files
AndrewSazonov May 8, 2020
d68abb1
Save calculations.cif to project
AndrewSazonov May 8, 2020
def44b3
Switch to master branch for cryspy
AndrewSazonov May 8, 2020
f71f4fa
Add calculations.cif
AndrewSazonov May 8, 2020
ffb5d3c
Intermediate fixes [ci skip]
wardsimon May 12, 2020
db37255
Re-write of DictComparison [ci skip]
wardsimon May 12, 2020
60a87ea
Fix unit tests and dictTools
wardsimon May 12, 2020
9c4b31a
fix fit tests on windows/linux
wardsimon May 13, 2020
923e7eb
More windows test fixes
wardsimon May 13, 2020
35a022b
Fix undo/redo for list types
wardsimon May 13, 2020
cc78bdd
More undo/redo work
wardsimon May 13, 2020
448d08a
Sort Backgrounds [ci skip]
wardsimon May 13, 2020
f9e2c3c
Ugly hack to save name/keyword changes
wardsimon May 13, 2020
fcffde2
Change keyword list to string
wardsimon May 13, 2020
6827f35
Sort background list of string keys numerically
AndrewSazonov May 14, 2020
6942174
Move filenames to master obj
wardsimon May 14, 2020
33a7099
Internal main_rcif to project_rcif
wardsimon May 14, 2020
814d836
Move from phases to samples
wardsimon May 14, 2020
f234aa7
Variable name changes
wardsimon May 14, 2020
b392f94
Rename phases to sample [ci skip]
AndrewSazonov May 14, 2020
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion Scripts/InstallPyPackages.py
Original file line number Diff line number Diff line change
Expand Up @@ -55,8 +55,9 @@ def install(*packages):

upgradePip()

installFromGit(owner='ikibalin', repo='cryspy', branch='transition-to-version-0.2', egg='cryspy_0.2.0_beta')
#installFromGit(owner='ikibalin', repo='cryspy', branch='transition-to-version-0.2', egg='cryspy_0.2.0_beta')
install(
'cryspy',
'dictdiffer',
'asteval',
'pytest',
Expand Down
718 changes: 472 additions & 246 deletions easyInterface/Diffraction/Calculators/CryspyCalculator.py

Large diffs are not rendered by default.

21 changes: 14 additions & 7 deletions easyInterface/Diffraction/DataClasses/DataObj/Calculation.py
Original file line number Diff line number Diff line change
Expand Up @@ -73,8 +73,15 @@ class CalculatedPattern(LoggedPathDict):
"""
Storage container for a calculated pattern
"""
def __init__(self, x: list, y_calc: list, y_diff_lower: list, y_diff_upper: list):
super().__init__(x=x, y_calc=y_calc, y_diff_lower=y_diff_lower, y_diff_upper=y_diff_upper)
def __init__(self, x: list, y_diff_lower: list, y_diff_upper: list, y_calc_up: list, y_calc_down: list = [], y_calc_bkg: list = []):
y_calc_down_temp = y_calc_down
if len(y_calc_down) == 0:
y_calc_down_temp = [0]*len(y_calc_up)

super().__init__(x=x, y_calc_sum=np.array(y_calc_up) + np.array(y_calc_down_temp), y_calc_diff=np.array(y_calc_up) - np.array(y_calc_down_temp),
y_calc_up=y_calc_up, y_calc_down=y_calc_down,
y_diff_lower=y_diff_lower, y_diff_upper=y_diff_upper,
y_calc_bkg=y_calc_bkg)
self._log = logging.getLogger(__class__.__module__)

def __repr__(self):
Expand All @@ -92,17 +99,17 @@ def __init__(self, name: str, bragg_peaks: BraggPeaks, calculated_pattern: Calcu
@classmethod
def default(cls, name: str):
bragg_peaks = BraggPeaks({})
calculated_pattern = CalculatedPattern([0], [0], [0], [0])
calculated_pattern = CalculatedPattern([0], [0], [0], [0],[0])
limits = Limits()
return cls(name, bragg_peaks, calculated_pattern, limits)

@classmethod
def fromPars(cls, name: str, bragg_crystals: CrystalBraggPeaks,
y_obs_lower: list, y_obs_upper: list,
tth: list, y_calc: list, y_diff_lower: list, y_diff_upper: list):
y_calc_lower: list, y_calc_upper: list,
tth: list, y_calc: list, y_diff_lower: list, y_diff_upper: list, y_calc_bkg: list):
bragg_peaks = BraggPeaks(bragg_crystals)
calculated_pattern = CalculatedPattern(tth, y_calc, y_diff_lower, y_diff_upper)
limits = Limits(y_obs_lower, y_obs_upper, y_diff_upper, y_diff_lower, x_calc=tth, y_calc=y_calc)
calculated_pattern = CalculatedPattern(tth, y_calc, y_diff_lower, y_diff_upper, y_calc_bkg)
limits = Limits(y_calc_lower, y_calc_upper, y_diff_upper, y_diff_lower, x_calc=tth, y_calc=y_calc)
return cls(name, bragg_peaks, calculated_pattern, limits)

def __repr__(self):
Expand Down
139 changes: 128 additions & 11 deletions easyInterface/Diffraction/DataClasses/DataObj/Experiment.py
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,12 @@
'tooltip': 'Degree offset in two theta',
'url': '',
'default': (0, 'deg')
},
'magnetic_field': {
'header': 'Field',
'tooltip': 'Applied magnetic field',
'url': '',
'default': (0, 'T')
}
}

Expand Down Expand Up @@ -48,11 +54,27 @@
}
}

POLARIZATION_DETAILS = {
'polarization': {
'header': '',
'tooltip': '',
'url': '',
'default': (1, '')
},
'efficiency': {
'header': '',
'tooltip': '',
'url': '',
'default': (1, '')
}
}


class Resolution(LoggedPathDict):
"""
Data store for the resolution parameters
"""

def __init__(self, u: Base, v: Base, w: Base, x: Base, y: Base):
"""
Dictionary store for resolution parameters
Expand Down Expand Up @@ -128,6 +150,7 @@ class Background(LoggedPathDict):
"""
Data store for the background data parameters
"""

def __init__(self, ttheta: float, intensity: Base):
"""
Background dictionary
Expand Down Expand Up @@ -173,6 +196,7 @@ class Backgrounds(ContainerObj):
"""
Store for a collection of background points
"""

def __init__(self, backgrounds: Union[Background, dict, list]):
"""
Constructor for Background data points
Expand All @@ -185,14 +209,24 @@ def __init__(self, backgrounds: Union[Background, dict, list]):
def __repr__(self):
return '{} Backgrounds'.format(len(self))

def sort(self, reverse=False):
keys = list(self.keys())
keys.sort(key=float, reverse=reverse)
new_bg = []
for key in keys:
new_bg.append(self[key])
super().__init__(new_bg, Background)


class MeasuredPattern(LoggedPathDict):
"""
Storage container for measured patterns
"""
def __init__(self, x: list, y_obs: list, sy_obs: list, y_obs_up: Union[list, None] = None,
sy_obs_up: Union[list, None] = None, y_obs_down: Union[list, None] = None,
sy_obs_down: Union[list, None] = None):

def __init__(self, x: list, y_obs: list, sy_obs: list,
y_obs_diff: Union[list, None] = None, sy_obs_diff: Union[list, None] = None,
y_obs_up: Union[list, None] = None, sy_obs_up: Union[list, None] = None,
y_obs_down: Union[list, None] = None, sy_obs_down: Union[list, None] = None):
"""
Constructor for a measured pattern

Expand All @@ -206,7 +240,8 @@ def __init__(self, x: list, y_obs: list, sy_obs: list, y_obs_up: Union[list, Non
"""
# 1d polarised powder diffraction data
# if y_obs_up is not None and sy_obs_up is not None and y_obs_down is not None and sy_obs_down is not None:
super().__init__(x=x, y_obs=y_obs, sy_obs=sy_obs, y_obs_up=y_obs_up, sy_obs_up=sy_obs_up,
super().__init__(x=x, y_obs=y_obs, sy_obs=sy_obs, y_obs_diff=y_obs_diff, sy_obs_diff=sy_obs_diff,
y_obs_up=y_obs_up, sy_obs_up=sy_obs_up,
y_obs_down=y_obs_down, sy_obs_down=sy_obs_down)
self._log = logging.getLogger(__class__.__module__)
# # 1d unpolarised powder diffraction data
Expand Down Expand Up @@ -254,22 +289,27 @@ def default(cls, polarised: bool = False):
x = []
y_obs = []
sy_obs = []
y_obs_diff = None
sy_obs_diff = None
y_obs_up = None
sy_obs_up = None
y_obs_down = None
sy_obs_down = None
if polarised:
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We should consider to make a enum with type of experiment, instead of using this boolean polarised.

y_obs_diff = []
sy_obs_diff = []
y_obs_up = []
sy_obs_up = []
y_obs_down = []
sy_obs_down = []
return cls(x, y_obs, sy_obs, y_obs_up, sy_obs_up, y_obs_down, sy_obs_down)
return cls(x, y_obs, sy_obs, y_obs_diff, sy_obs_diff, y_obs_up, sy_obs_up, y_obs_down, sy_obs_down)


class ExperimentPhase(LoggedPathDict):
"""
Storage container for the Experimental Phase details
"""

def __init__(self, name: str, scale: Base):
"""
Constructor for the Experimental phase container
Expand All @@ -278,9 +318,11 @@ def __init__(self, name: str, scale: Base):
"""
super().__init__(name=name, scale=scale)
self._log = logging.getLogger(__class__.__module__)

self.setItemByPath(['scale', 'header'], SCALE_DETAILS['scale']['header'])
self.setItemByPath(['scale', 'tooltip'], SCALE_DETAILS['scale']['tooltip'])
self.setItemByPath(['scale', 'url'], SCALE_DETAILS['scale']['url'])

self._log.debug('Created phase: {}'.format(self))

@classmethod
Expand Down Expand Up @@ -311,6 +353,7 @@ class ExperimentPhases(ContainerObj):
"""
Storage of multiple phase markers associated with experiments
"""

def __init__(self, experiment_phases: Union[list, ExperimentPhase, dict]):
"""
Constructor for holding multiple experiments
Expand All @@ -324,11 +367,69 @@ def __repr__(self) -> str:
return '{} Experimental phases'.format(len(self))


class RefinementType(LoggedPathDict):
_default = {'_sum': False, '_diff': False}

def __init__(self):
super().__init__(**self._default)
self.object = None

def set_object(self, obj):
self.object = obj

@property
def sum(self):
return self['_sum']

@sum.setter
def sum(self, value):
if self.object is not None:
self.object.sum = value
self['_sum'] = value

@property
def diff(self):
return self['_diff']

@diff.setter
def diff(self, value):
if self.object is not None:
self.object.diff = value
self['_diff'] = value


class Polarization(LoggedPathDict):
def __init__(self, polarization: Base, efficiency: Base):
super().__init__(polarization=polarization, efficiency=efficiency)

self.setItemByPath(['polarization', 'header'], POLARIZATION_DETAILS['polarization']['header'])
self.setItemByPath(['polarization', 'tooltip'], POLARIZATION_DETAILS['polarization']['tooltip'])
self.setItemByPath(['polarization', 'url'], POLARIZATION_DETAILS['polarization']['url'])

self.setItemByPath(['efficiency', 'header'], POLARIZATION_DETAILS['efficiency']['header'])
self.setItemByPath(['efficiency', 'tooltip'], POLARIZATION_DETAILS['efficiency']['tooltip'])
self.setItemByPath(['efficiency', 'url'], POLARIZATION_DETAILS['efficiency']['url'])

@classmethod
def default(cls):
polarization = Base(*POLARIZATION_DETAILS['polarization']['default'])
efficiency = Base(*POLARIZATION_DETAILS['efficiency']['default'])
return cls(polarization, efficiency)

@classmethod
def fromPars(cls, polarization, efficiency):
polarization = Base(polarization, POLARIZATION_DETAILS['polarization']['default'][1])
efficiency = Base(efficiency, POLARIZATION_DETAILS['efficiency']['default'][1])
return cls(polarization, efficiency)


class Experiment(LoggedPathDict):
"""
Experimental details data container
"""
def __init__(self, name: str, wavelength: Base, offset: Base, phase: ExperimentPhases, background: Backgrounds,

def __init__(self, name: str, wavelength: Base, offset: Base, magnetic_field: Base, phase: ExperimentPhases,
background: Backgrounds,
resolution: Resolution, measured_pattern: MeasuredPattern):
"""
Constructor for experimental data container
Expand All @@ -341,8 +442,14 @@ def __init__(self, name: str, wavelength: Base, offset: Base, phase: ExperimentP
:param resolution: Description of the resolution
:param measured_pattern: What was actually measured
"""
super().__init__(name=name, wavelength=wavelength, offset=offset, phase=phase, background=background,
resolution=resolution, measured_pattern=measured_pattern)

refinement_type = RefinementType()
refinement_type.sum = True

super().__init__(name=name, wavelength=wavelength, offset=offset, magnetic_field=magnetic_field, phase=phase,
background=background,
resolution=resolution, measured_pattern=measured_pattern, refinement_type=refinement_type,
polarization=Polarization.default())
self._log = logging.getLogger(__class__.__module__)

self.setItemByPath(['wavelength', 'header'], EXPERIMENT_DETAILS['wavelength']['header'])
Expand All @@ -353,6 +460,10 @@ def __init__(self, name: str, wavelength: Base, offset: Base, phase: ExperimentP
self.setItemByPath(['offset', 'tooltip'], EXPERIMENT_DETAILS['offset']['tooltip'])
self.setItemByPath(['offset', 'url'], EXPERIMENT_DETAILS['offset']['url'])

self.setItemByPath(['magnetic_field', 'header'], EXPERIMENT_DETAILS['magnetic_field']['header'])
self.setItemByPath(['magnetic_field', 'tooltip'], EXPERIMENT_DETAILS['magnetic_field']['tooltip'])
self.setItemByPath(['magnetic_field', 'url'], EXPERIMENT_DETAILS['magnetic_field']['url'])

@classmethod
def default(cls, name: str) -> 'Experiment':
"""
Expand All @@ -363,15 +474,16 @@ def default(cls, name: str) -> 'Experiment':
"""
wavelength = Base(*EXPERIMENT_DETAILS['wavelength']['default'])
offset = Base(*EXPERIMENT_DETAILS['offset']['default'])
field = Base(*EXPERIMENT_DETAILS['magnetic_field']['default'])
phase = ExperimentPhases({})
backgrounds = Backgrounds(Background.default())
resolution = Resolution.default()
measured_pattern = MeasuredPattern.default()
return cls(name, wavelength, offset, phase, backgrounds, resolution, measured_pattern)
return cls(name, wavelength, offset, field, phase, backgrounds, resolution, measured_pattern)

@classmethod
def fromPars(cls, name: str, wavelength: float, offset: float, scale: float, background: Backgrounds,
resolution: Resolution, measured_pattern: MeasuredPattern) -> 'Experiment':
resolution: Resolution, measured_pattern: MeasuredPattern, magnetic_field: float = None) -> 'Experiment':
"""
Constructor of experiment from parameters

Expand All @@ -386,8 +498,12 @@ def fromPars(cls, name: str, wavelength: float, offset: float, scale: float, bac
"""
wavelength = Base(wavelength, EXPERIMENT_DETAILS['wavelength']['default'][1])
offset = Base(offset, EXPERIMENT_DETAILS['offset']['default'][1])
if magnetic_field is None:
magnetic_field = Base(*EXPERIMENT_DETAILS['magnetic_field']['default'])
else:
magnetic_field = Base(magnetic_field, EXPERIMENT_DETAILS['magnetic_field']['default'][1])
phase = ExperimentPhases(ExperimentPhase.fromPars(name, scale))
return cls(name, wavelength, offset, phase, background, resolution, measured_pattern)
return cls(name, wavelength, offset, magnetic_field, phase, background, resolution, measured_pattern)

def __repr__(self):
return 'Experiment: {}'.format(self['name'])
Expand All @@ -397,6 +513,7 @@ class Experiments(ContainerObj):
"""
Container for multiple experiments
"""

def __init__(self, experiments: Union[Experiment, dict, list]):
"""
Constructor for holding multiple experiments
Expand Down
2 changes: 1 addition & 1 deletion easyInterface/Diffraction/DataClasses/PhaseObj/Atom.py
Original file line number Diff line number Diff line change
Expand Up @@ -169,7 +169,7 @@ def fromXYZ(cls, atom_site_label: str, type_symbol: str, x: float, y: float, z:
return obj

@classmethod
def fromPars(cls, atom_site_label: str, type_symbol: str, scat_length_neutron: float,
def fromPars(cls, atom_site_label: str, type_symbol: str, scat_length_neutron: complex,
fract_x: float, fract_y: float, fract_z: float, occupancy: float, adp_type: str,
U_iso_or_equiv: float, ADp: list = None, MSp: list = None) -> 'Atom':
"""
Expand Down
Loading