| Previous changeset 0:ae2f265ecf8e (2023-11-14) Next changeset 2:a1e26990131c (2024-03-04) |
|
Commit message:
planemo upload for repository https://github.com/MaterialsGalaxy/larch-tools/tree/main/larch_athena commit 1cf6d7160497ba58fe16a51f00d088a20934eba6 |
|
modified:
common.py larch_athena.py larch_athena.xml macros.xml |
|
added:
test-data/ffi1.tabular test-data/multiple.prj |
| b |
| diff -r ae2f265ecf8e -r 2b3115342fef common.py --- a/common.py Tue Nov 14 15:34:40 2023 +0000 +++ b/common.py Wed Dec 06 13:03:55 2023 +0000 |
| [ |
| @@ -7,38 +7,145 @@ def get_group(athena_group: AthenaGroup, key: str = None) -> Group: + group_keys = list(athena_group._athena_groups.keys()) if key is None: - group_keys = list(athena_group._athena_groups.keys()) key = group_keys[0] - return extract_athenagroup(athena_group._athena_groups[key]) + else: + key = key.replace("-", "_") + + try: + return extract_athenagroup(athena_group._athena_groups[key]) + except KeyError as e: + raise KeyError(f"{key} not in {group_keys}") from e + + +def read_all_groups(dat_file: str, key: str = None) -> "dict[str, Group]": + # Cannot rely on do_ABC as _larch is None + athena_group = read_athena( + dat_file, + do_preedge=False, + do_bkg=False, + do_fft=False, + ) + all_groups = {} + for key in athena_group._athena_groups.keys(): + group = get_group(athena_group, key) + pre_edge_with_defaults(group=group) + xftf_with_defaults(group=group) + all_groups[key] = group + + return all_groups + + +def read_group(dat_file: str, key: str = None): + # Cannot rely on do_ABC as _larch is None + athena_group = read_athena( + dat_file, + do_preedge=False, + do_bkg=False, + do_fft=False, + ) + group = get_group(athena_group, key) + pre_edge_with_defaults(group=group) + xftf_with_defaults(group=group) + return group -def read_group(dat_file: str, key: str = None, xftf_params: dict = None): - athena_group = read_athena(dat_file) - group = get_group(athena_group, key) - bkg_parameters = group.athena_params.bkg - print(group.athena_params.fft) - print(group.athena_params.fft.__dict__) - pre_edge( - group, - e0=bkg_parameters.e0, - pre1=bkg_parameters.pre1, - pre2=bkg_parameters.pre2, - norm1=bkg_parameters.nor1, - norm2=bkg_parameters.nor2, - nnorm=bkg_parameters.nnorm, - make_flat=bkg_parameters.flatten, +def pre_edge_with_defaults(group: Group, settings: dict = None): + merged_settings = {} + try: + bkg_parameters = group.athena_params.bkg + except AttributeError as e: + print(f"Cannot load group.athena_params.bkg from group:\n{e}") + bkg_parameters = None + + keys = ( + ("e0", "e0", None), + ("pre1", "pre1", None), + ("pre2", "pre2", None), + ("norm1", "nor1", None), + ("norm2", "nor2", None), + ("nnorm", "nnorm", None), + ("make_flat", "flatten", None), + ("step", "step", None), + # This cannot be read from file as it is not stored by Larch (0.9.71) + # ("nvict", "nvict", None), ) - autobk(group) - if xftf_params is None: - xftf(group) - else: - print(xftf_params) - xftf(group, **xftf_params) - xftf_details = Group() - setattr(xftf_details, "call_args", xftf_params) - group.xftf_details = xftf_details - return group + for key, parameters_key, default in keys: + extract_attribute( + merged_settings, key, bkg_parameters, parameters_key, default + ) + + if settings: + for k, v in settings.items(): + if k == "nvict": + print( + "WARNING: `nvict` can be used for pre-edge but is not " + "saved to file, so value used will not be accessible in " + "future operations using this Athena .prj" + ) + merged_settings[k] = v + + print(f"Pre-edge normalization with {merged_settings}") + try: + pre_edge(group, **merged_settings) + except Warning as e: + raise Warning( + "Unable to perform pre-edge fitting with:\n\n" + f"energy:\n{group.energy}\n\nmu:{group.mu}\n\n" + "Consider checking the correct columns have been extracted" + ) from e + autobk(group, pre_edge_kws=merged_settings) + + +def xftf_with_defaults(group: Group, settings: dict = None): + merged_settings = {} + try: + fft_parameters = group.athena_params.fft + except AttributeError as e: + print(f"Cannot load group.athena_params.fft from group:\n{e}") + fft_parameters = None + + keys = ( + ("kmin", "kmin", 0), + ("kmax", "kmax", 20), + ("dk", "dk", 1), + ("kweight", "kw", 2), + ("kweight", "kweight", 2), + ("window", "kwindow", "kaiser"), + ) + for key, parameters_key, default in keys: + extract_attribute( + merged_settings, key, fft_parameters, parameters_key, default + ) + + if settings: + for k, v in settings.items(): + merged_settings[k] = v + + print(f"XFTF with {merged_settings}") + xftf(group, **merged_settings) + xftf_details = Group() + setattr(xftf_details, "call_args", merged_settings) + group.xftf_details = xftf_details + + +def extract_attribute( + merged_settings: dict, + key: str, + parameters_group: Group, + parameters_key: str, + default: "str|int" = None, +): + if parameters_group is not None: + try: + merged_settings[key] = getattr(parameters_group, parameters_key) + return + except AttributeError: + pass + + if default is not None: + merged_settings[key] = default def read_groups(dat_files: "list[str]", key: str = None) -> Iterable[Group]: |
| b |
| diff -r ae2f265ecf8e -r 2b3115342fef larch_athena.py --- a/larch_athena.py Tue Nov 14 15:34:40 2023 +0000 +++ b/larch_athena.py Wed Dec 06 13:03:55 2023 +0000 |
| [ |
| b'@@ -4,7 +4,9 @@\n import re\n import sys\n \n-from common import read_group\n+from common import (\n+ pre_edge_with_defaults, read_all_groups, read_group, xftf_with_defaults\n+)\n \n from larch.io import (\n create_athena,\n@@ -14,7 +16,7 @@\n set_array_labels,\n )\n from larch.symboltable import Group\n-from larch.xafs import autobk, pre_edge, rebin_xafs, xftf\n+from larch.xafs import rebin_xafs\n \n import matplotlib\n import matplotlib.pyplot as plt\n@@ -27,13 +29,11 @@\n self,\n energy_column: str,\n mu_column: str,\n- xftf_params: dict,\n data_format: str,\n- extract_group: str = None,\n+ extract_group: "dict[str, str]" = None,\n ):\n self.energy_column = energy_column\n self.mu_column = mu_column\n- self.xftf_params = xftf_params\n self.data_format = data_format\n self.extract_group = extract_group\n \n@@ -72,13 +72,24 @@\n self,\n filepath: str,\n is_zipped: bool = False,\n- ) -> "dict[str,Group]":\n+ ) -> "tuple[dict, bool]":\n if is_zipped:\n return self.load_zipped_files()\n \n print(f"Attempting to read from {filepath}")\n if self.data_format == "athena":\n- group = read_group(filepath, self.extract_group, self.xftf_params)\n+ if self.extract_group["extract_group"] == "single":\n+ group = read_group(filepath, self.extract_group["group_name"])\n+ return {"out": group}\n+ elif self.extract_group["extract_group"] == "multiple":\n+ groups = {}\n+ for repeat in self.extract_group["multiple"]:\n+ name = repeat["group_name"]\n+ groups[name] = read_group(filepath, name)\n+ return groups\n+ else:\n+ return read_all_groups(filepath)\n+\n else:\n # Try ascii anyway\n try:\n@@ -90,7 +101,9 @@\n except (UnicodeDecodeError, TypeError):\n # Indicates this isn\'t plaintext, try h5\n group = self.load_h5(filepath)\n- return {"out": group}\n+ pre_edge_with_defaults(group)\n+ xftf_with_defaults(group)\n+ return {"out": group}\n \n def load_ascii(self, dat_file):\n with open(dat_file) as f:\n@@ -156,27 +169,27 @@\n \n if "energy" in labels:\n print("\'energy\' present in column headers")\n- elif self.energy_column is not None:\n+ elif self.energy_column:\n if self.energy_column.lower() in labels:\n labels[labels.index(self.energy_column.lower())] = "energy"\n else:\n raise ValueError(f"{self.energy_column} not found in {labels}")\n else:\n for i, label in enumerate(labels):\n- if label == "col1" or label.endswith("energy"):\n+ if label in ("col1", "ef") or label.endswith("energy"):\n labels[i] = "energy"\n break\n \n if "mu" in labels:\n print("\'mu\' present in column headers")\n- elif self.mu_column is not None:\n+ elif self.mu_column:\n if self.mu_column.lower() in labels:\n labels[labels.index(self.mu_column.lower())] = "mu"\n else:\n raise ValueError(f"{self.mu_column} not found in {labels}")\n else:\n for i, label in enumerate(labels):\n- if label in ["col2", "xmu", "lni0it", "ffi0"]:\n+ if label in ["col2", "xmu", "lni0it", "ffi0", "ff/i1"]:\n labels[i] = "mu"\n break\n \n@@ -189,29 +202,24 @@\n \n def calibrate_energy(\n xafs_group: Group,\n- energy_0: float,\n- energy_min: float,\n- energy_max: float,\n- energy_format: str,\n+ calibration_e0: float = None,\n+ energy_min: float = None,\n+ energy_max: float = None,\n ):\n- if energy_0 is not None:\n- print(f"Recalibrating energy edge from {xafs_gr'..b'xas_data.mu,\n+ group=xas_data,\n+ **pre_edge_settings,\n+ )\n+ xas_data = xas_data.rebinned\n+ # After re-bin, will need to redo pre-edge\n+ do_pre_edge = True\n \n- if input_values["rebin"]:\n- print(xas_data.energy, xas_data.mu)\n- rebin_xafs(energy=xas_data.energy, mu=xas_data.mu, group=xas_data)\n- xas_data = xas_data.rebinned\n- pre_edge(energy=xas_data.energy, mu=xas_data.mu, group=xas_data)\n+ if do_pre_edge:\n+ pre_edge_with_defaults(xas_data, pre_edge_settings)\n \n- try:\n- autobk(xas_data)\n- except ValueError as e:\n- raise ValueError(\n- f"autobk failed with energy={xas_data.energy}, mu={xas_data.mu}.\\n"\n- "This may occur if the edge is not included in the above ranges."\n- ) from e\n- xftf(xas_data, **xftf_params)\n+ if do_xftf:\n+ xftf_with_defaults(xas_data, xftf_settings)\n \n- if input_values["plot_graph"]:\n+ if plot_graph:\n plot_edge_fits(f"edge/{path_key}.png", xas_data)\n plot_flattened(f"flat/{path_key}.png", xas_data)\n plot_derivative(f"derivative/{path_key}.png", xas_data)\n \n xas_project = create_athena(f"prj/{path_key}.prj")\n xas_project.add_group(xas_data)\n- if input_values["annotation"]:\n+ if annotation:\n group = next(iter(xas_project.groups.values()))\n- group.args["annotation"] = input_values["annotation"]\n+ group.args["annotation"] = annotation\n xas_project.save()\n \n # Ensure that we do not run out of memory when running on large zips\n gc.collect()\n \n \n-def validate_pre(pre, energy_0, energy_format):\n- if pre is not None and energy_format == "absolute":\n- if energy_0 is None:\n- raise ValueError(\n- "Edge energy must be set manually or be present in the "\n- "existing Athena project if using absolute format."\n- )\n- pre -= energy_0\n-\n- return pre\n-\n-\n def plot_derivative(plot_path: str, xafs_group: Group):\n plt.figure()\n plt.plot(xafs_group.energy, xafs_group.dmude)\n@@ -363,9 +347,8 @@\n )\n else:\n is_zipped = False\n- xftf_params = input_values["variables"]["xftf"]\n+\n extract_group = None\n-\n if "extract_group" in input_values["merge_inputs"]["format"]:\n extract_group = input_values["merge_inputs"]["format"]["extract_group"]\n \n@@ -379,7 +362,6 @@\n reader = Reader(\n energy_column=energy_column,\n mu_column=mu_column,\n- xftf_params=xftf_params,\n data_format=data_format,\n extract_group=extract_group,\n )\n@@ -388,9 +370,35 @@\n merge_inputs=merge_inputs,\n is_zipped=is_zipped,\n )\n+\n+ calibrate_items = input_values["processing"]["calibrate"].items()\n+ calibrate_settings = {k: v for k, v in calibrate_items if v is not None}\n+ do_calibrate = calibrate_settings.pop("calibrate") == "true"\n+\n+ do_rebin = input_values["processing"].pop("rebin")\n+\n+ pre_edge_items = input_values["processing"]["pre_edge"].items()\n+ pre_edge_settings = {k: v for k, v in pre_edge_items if v is not None}\n+ do_pre_edge = pre_edge_settings.pop("pre_edge") == "true"\n+\n+ xftf_items = input_values["processing"]["xftf"].items()\n+ xftf_settings = {k: v for k, v in xftf_items if v is not None}\n+ do_xftf = xftf_settings.pop("xftf") == "true"\n+\n+ plot_graph = input_values["plot_graph"]\n+ annotation = input_values["annotation"]\n+\n for key, group in keyed_data.items():\n main(\n group,\n- input_values=input_values,\n+ do_calibrate=do_calibrate,\n+ calibrate_settings=calibrate_settings,\n+ do_rebin=do_rebin,\n+ do_pre_edge=do_pre_edge,\n+ pre_edge_settings=pre_edge_settings,\n+ do_xftf=do_xftf,\n+ xftf_settings=xftf_settings,\n+ plot_graph=plot_graph,\n+ annotation=annotation,\n path_key=key,\n )\n' |
| b |
| diff -r ae2f265ecf8e -r 2b3115342fef larch_athena.xml --- a/larch_athena.xml Tue Nov 14 15:34:40 2023 +0000 +++ b/larch_athena.xml Wed Dec 06 13:03:55 2023 +0000 |
| [ |
| b'@@ -4,7 +4,7 @@\n <!-- version of underlying tool (PEP 440) -->\n <token name="@TOOL_VERSION@">0.9.71</token>\n <!-- version of this tool wrapper (integer) -->\n- <token name="@WRAPPER_VERSION@">0</token>\n+ <token name="@WRAPPER_VERSION@">1</token>\n <!-- citation should be updated with every underlying tool version -->\n <!-- typical fields to update are version, month, year, and doi -->\n <token name="@TOOL_CITATION@">10.1088/1742-6596/430/1/012007</token>\n@@ -15,11 +15,26 @@\n </param> \n </xml>\n <xml name="extract_group">\n- <param name="extract_group" type="text" optional="true" label="Extract group" help="Which group to extract and process from the Athena project (will use first group in file if unset)"/>\n+ <conditional name="extract_group">\n+ <param name="extract_group" type="select" label="Group extraction" help="Method of handling group extraction. Extracting all or multiple named groups will result in multiple outputs, unless merging groups is also true.">\n+ <option value="single" selected="true">Extract single</option>\n+ <option value="multiple">Extract multiple</option>\n+ <option value="all">Extract all</option>\n+ </param>\n+ <when value="single">\n+ <param name="group_name" type="text" optional="true" label="Group label" help="Which group to extract and process from the Athena project (will use first group in file if unset)"/>\n+ </when>\n+ <when value="multiple">\n+ <repeat name="multiple" min="1" default="1" title="Groups">\n+ <param name="group_name" type="text" label="Group label" help="Which group to extract and process from the Athena project (will use first group in file if unset)"/>\n+ </repeat>\n+ </when>\n+ <when value="all"/>\n+ </conditional>\n </xml>\n <xml name="columns">\n- <param name="energy_column" type="text" optional="true" label="Energy column" help="If set, this column we be used as \'energy\'. Otherwise, will identify columns ending with \'energy\' or labelled \'col1\'."/>\n- <param name="mu_column" type="text" optional="true" label="\xce\xbc column" help="If set, this column we be used as \'mu\'. Otherwise, will identify the first column labelled as either \'col2\', \'xmu\', \'lni0it\' or \'FFI0\'."/>\n+ <param name="energy_column" type="text" optional="true" label="Energy column" help="If set, this column we be used as \'energy\'. Otherwise, will identify the first column ending with \'energy\' or labelled \'col1\' \'Ef\'."/>\n+ <param name="mu_column" type="text" optional="true" label="\xce\xbc column" help="If set, this column we be used as \'mu\'. Otherwise, will identify the first column labelled as either \'col2\', \'xmu\', \'lni0it\', \'FFI0\' or \'FF/I1\'."/>\n </xml>\n <xml name="is_zipped">\n <param name="is_zipped" type="select" display="radio" label="Inputs Zipped" help="Whether plaintext input files are zipped together into one directory, or not.">\n@@ -40,6 +55,7 @@\n </requirements>\n <required_files>\n <include type="literal" path="larch_athena.py"/>\n+ <include type="literal" path="common.py"/>\n </required_files>\n <command detect_errors="exit_code"><![CDATA[\n mkdir prj edge flat derivative\n@@ -111,16 +127,55 @@\n </when>\n </conditional>\n <param name="annotation" type="text" label="Annotation" optional="true" help="If set, will annotate the output project(s) with this string. This will be used to generate legends when plotting data."/>\n- <section name="variables" title="Processing Options">\n- <param name="energy_0" type="float" label="Edge energy (eV)" optional="true" help="If set, data will be calibrated so that the edge occur'..b'"4">\n <param name="dat_file" value="test.xmu"/>\n- <param name="energy_format" value="absolute"/>\n+ <param name="calibrate" value="true"/>\n <param name="energy_min" value="7000"/>\n <param name="energy_max" value="7200"/>\n <param name="plot_graph" value="true"/>\n@@ -259,32 +329,34 @@\n </output>\n <output name="edge_plot">\n <assert_contents>\n- <has_size value="44430" delta="10"/>\n+ <has_size value="44900" delta="100"/>\n </assert_contents>\n </output>\n <output name="flat_plot">\n <assert_contents>\n- <has_size value="37310" delta="10"/>\n+ <has_size value="39400" delta="100"/>\n </assert_contents>\n </output>\n <output name="derivative_plot">\n <assert_contents>\n- <has_size value="46390" delta="10"/>\n+ <has_size value="45900" delta="100"/>\n </assert_contents>\n </output>\n </test>\n+ <!-- 9 -->\n <test expect_num_outputs="1">\n <param name="dat_file" value="test.xmu"/>\n- <param name="energy_format" value="absolute"/>\n- <param name="energy_0" value="7050"/>\n+ <param name="calibrate" value="true"/>\n+ <param name="calibration_e0" value="7050"/>\n <param name="energy_min" value="7000"/>\n <param name="energy_max" value="7200"/>\n <output name="athena_project_file">\n <assert_contents>\n- <has_size value="3300" delta="50"/>\n+ <has_size value="3600" delta="100"/>\n </assert_contents>\n </output>\n </test>\n+ <!-- 10 -->\n <test expect_num_outputs="1">\n <param name="dat_file" value="test.xmu"/>\n <param name="rebin" value="true"/>\n@@ -294,6 +366,7 @@\n </assert_contents>\n </output>\n </test>\n+ <!-- 11 -->\n <test expect_num_outputs="1">\n <param name="merge_inputs" value="true"/>\n <param name="dat_file" value="262875_PtSn_OCO_Abu_1.nxs,262876_PtSn_OCO_Abu_2.nxs"/>\n@@ -303,6 +376,7 @@\n </assert_contents>\n </output>\n </test>\n+ <!-- 12 -->\n <test expect_num_outputs="1">\n <param name="merge_inputs" value="true"/>\n <param name="is_zipped" value="true"/>\n@@ -313,6 +387,7 @@\n </assert_contents>\n </output>\n </test>\n+ <!-- 13 -->\n <test expect_num_outputs="1">\n <param name="format" value="athena"/>\n <param name="dat_file" value="test.prj"/>\n@@ -322,6 +397,22 @@\n </assert_contents>\n </output>\n </test>\n+ <!-- 14: Extract multiple groups from Athena .prj -->\n+ <test expect_num_outputs="1">\n+ <param name="format" value="athena"/>\n+ <param name="extract_group" value="multiple"/>\n+ <param name="group_name" value="merge"/>\n+ <param name="group_name" value="d__Ref_PtSn_OC_MERGE_CALIBRATE"/>\n+ <param name="dat_file" value="multiple.prj"/>\n+ <output_collection name="athena_project_file_collection" type="list" count="2"/>\n+ </test>\n+ <!-- 15: Extract all groups from Athena .prj -->\n+ <test expect_num_outputs="1">\n+ <param name="format" value="athena"/>\n+ <param name="extract_group" value="all"/>\n+ <param name="dat_file" value="multiple.prj"/>\n+ <output_collection name="athena_project_file_collection" type="list" count="9"/>\n+ </test>\n </tests>\n <help><![CDATA[\n Using Larch, create an Athena project file from the input X-ray Absorption Fine Structure (XAFS) data file.\n' |
| b |
| diff -r ae2f265ecf8e -r 2b3115342fef macros.xml --- a/macros.xml Tue Nov 14 15:34:40 2023 +0000 +++ b/macros.xml Wed Dec 06 13:03:55 2023 +0000 |
| b |
| @@ -1,26 +1,6 @@ <macros> - <xml name="energy_limits"> - <param name="energy_format" type="select" display="radio" label="Energy limits" help="Whether to limit the energy relative to the absorption edge or with absolute values."> - <option value="relative" selected="true">Relative</option> - <option value="absolute">Absolute</option> - </param> - <param name="energy_min" type="float" label="Minimum energy (eV)" optional="true" help="If set, data will be cropped below this value in electron volts."/> - <param name="energy_max" type="float" label="Maximum energy (eV)" optional="true" help="If set, data will be cropped above this value in electron volts."/> - </xml> - <xml name="xftf_params"> - <param argument="kmin" type="float" value="0" min="0.0" help="Minimum k value."/> - <param argument="kmax" type="float" value="20" min="0.0" help="Maximum k value."/> - <param argument="kweight" type="float" value="2" help="Exponent for weighting spectra by raising k to this power."/> - <param argument="dk" type="float" value="4" help="Tapering parameter for Fourier Transform window."/> - <param argument="window" type="select" help="Fourier Transform window type."> - <option value="hanning">Hanning (cosine-squared taper)</option> - <option value="parzen">Parzen (linear taper)</option> - <option value="welch">Welch (quadratic taper)</option> - <option value="gaussian">Gaussian function window</option> - <option value="sine">Sine function window</option> - <option value="kaiser" selected="true">Kaiser-Bessel function-derived window</option> - </param> - <param argument="rmin" type="float" value="0.0" min="0.0" help="Minimum radial distance."/> - <param argument="rmax" type="float" value="10.0" min="0.0" help="Maximum radial distance."/> + <xml name="plot_limits_energy"> + <param name="x_limit_min" type="float" label="Minimum plot energy (eV)" optional="true" help="If set, plot will be limited to this value on the x axis."/> + <param name="x_limit_max" type="float" label="Maximum plot energy (eV)" optional="true" help="If set, plot will be limited to this value on the x axis."/> </xml> </macros> \ No newline at end of file |
| b |
| diff -r ae2f265ecf8e -r 2b3115342fef test-data/ffi1.tabular --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/test-data/ffi1.tabular Wed Dec 06 13:03:55 2023 +0000 |
| b |
| b'@@ -0,0 +1,355 @@\n+# Energy \tFF/I1 \tTime\n+ 6911.8277 0.80926541 272002.00\n+ 6916.9236 0.80418730 270032.00\n+ 6921.7638 0.79959074 268827.00\n+ 6926.8750 0.79459529 267514.00\n+ 6931.7907 0.79004613 255214.00\n+\n+ 6962.0000 0.78791063 305150.00\n+ 6972.0000 0.77475191 306445.00\n+ 6982.0000 0.76169076 306446.00\n+ 6992.0000 0.74992551 306744.00\n+ 7002.0000 0.73660315 306246.00\n+ 7012.0000 0.72423404 306358.00\n+ 7022.0000 0.71196509 306309.00\n+ 7032.0000 0.70002723 306019.00\n+ 7042.0000 0.68735767 306529.00\n+ 7052.0000 0.67439453 306124.00\n+ 7062.0000 0.66235517 306188.00\n+ 7072.0000 0.65022361 306119.00\n+ 7082.0000 0.63942705 306143.00\n+ 7092.0000 0.62824650 306098.00\n+ 7092.5000 0.62753795 305825.00\n+ 7093.0000 0.62748380 305756.00\n+ 7093.5000 0.62785219 305745.00\n+ 7094.0000 0.62636441 305717.00\n+ 7094.5000 0.62575793 305670.00\n+ 7095.0000 0.62551244 305666.00\n+ 7095.5000 0.62515947 305631.00\n+ 7096.0000 0.62492947 305585.00\n+ 7096.5000 0.62367544 305536.00\n+ 7097.0000 0.62332504 305539.00\n+ 7097.5000 0.62259547 305510.00\n+ 7098.0000 0.62252464 305466.00\n+ 7098.5000 0.62240279 305494.00\n+ 7099.0000 0.62172416 305432.00\n+ 7099.5000 0.62098768 305503.00\n+ 7100.0000 0.62118707 305402.00\n+ 7100.5000 0.62045272 305414.00\n+ 7101.0000 0.62040785 305391.00\n+ 7101.5000 0.62002332 305400.00\n+ 7102.0000 0.61932445 305952.00\n+ 7102.5000 0.61954721 305420.00\n+ 7103.0000 0.61934375 304860.00\n+ 7103.5000 0.61907141 305180.00\n+ 7104.0000 0.61843263 305180.00\n+ 7104.5000 0.61879967 305435.00\n+ 7105.0000 0.61854579 305144.00\n+ 7105.5000 0.61837948 305045.00\n+ 7106.0000 0.61887282 304943.00\n+ 7106.5000 0.61837848 305015.00\n+ 7107.0000 0.61844121 305023.00\n+ 7107.5000 0.61908174 304990.00\n+ 7108.0000 0.62025344 305117.00\n+ 7108.5000 0.62083284 305305.00\n+ 7109.0000 0.62279082 304852.00\n+ 7109.5000 0.62484776 304938.00\n+ 7110.0000 0.63029578 305214.00\n+ 7110.5000 0.63827614 304831.00\n+ 7111.0000 0.65354125 304668.00\n+ 7111.5000 0.67171017 304489.00\n+ 7112.0000 0.68465719 304804.00\n+ 7112.5000 0.68977450 304821.00\n+ 7113.0000 0.68982223 304700.00\n+ 7113.5000 0.68880150 304652.00\n+ 7114.0000 0.68631667 304907.00\n+ 7114.5000 0.68636382 304536.00\n+ 7115.0000 0.69345881 305540.00\n+ 7115.5000 0.71368054 306249.00\n+ 7116.0000 0.75470012 306100.00\n+ 7116.5000 0.82334644 305917.00\n+ 7117.0000 0.91897755 306536.00\n+ 7117.5000 1.0048919 306925.00\n+ 7118.0000 1.0613446 306741.00\n+ 7118.5000 1.1171460 306475.00\n+ 7119.0000 1.1598287 306428.00\n+ 7119.5000 1.1845153 306460.00\n+ 7120.0000 1.1839175 306450.00\n+ 7120.5000 1.1705836 306582.00\n+ 7121.0000 1.1532435 306359.00\n+ 7121.5000 1.1455536 306364.00\n+ 7122.0000 1.1474359 306349.00\n+ 7122.5000 1.1522733 306255.00\n+ 7123.0000 1.1570854 306266.00\n+ 7123.5000 1.1609012 306230.00\n+ 7124.0000 1.1633654 306227.00\n+ 7124.5000 1.1626865 30637'..b'93523 305560.00\n+ 7560.2820 0.74539760 305668.00\n+ 7564.4270 0.74088376 305785.00\n+ 7568.5910 0.73831944 305684.00\n+ 7572.7740 0.73529922 305582.00\n+ 7576.9770 0.73187551 305523.00\n+ 7581.1980 0.72922440 305558.00\n+ 7585.4390 0.72676436 305647.00\n+ 7589.6980 0.72359612 305208.00\n+ 7593.9770 0.71807714 306038.00\n+ 7598.2750 0.71252104 305315.00\n+ 7602.5920 0.70549579 305573.00\n+ 7606.9280 0.69954396 305378.00\n+ 7611.2830 0.69265029 305425.00\n+ 7615.6570 0.68689223 305488.00\n+ 7620.0500 0.68092659 305297.00\n+ 7624.4620 0.67499882 305001.00\n+ 7628.8940 0.66889046 305246.00\n+ 7633.3440 0.66341014 305391.00\n+ 7637.8130 0.65798296 305277.00\n+ 7642.3020 0.65352747 305129.00\n+ 7646.8100 0.64842668 305185.00\n+ 7651.3360 0.64433064 305107.00\n+ 7655.8820 0.64130624 304968.00\n+ 7660.4470 0.63726602 303292.00\n+ 7665.0300 0.63282645 306701.00\n+ 7669.6340 0.62771419 304931.00\n+ 7674.2550 0.62136047 304917.00\n+ 7678.8960 0.61572914 304978.00\n+ 7683.5570 0.61094428 305007.00\n+ 7688.2360 0.60604922 304909.00\n+ 7692.9350 0.60062272 304867.00\n+ 7697.6520 0.59482509 304843.00\n+ 7702.3890 0.58954937 304732.00\n+ 7707.1440 0.58505148 304761.00\n+ 7711.9190 0.58034243 304780.00\n+ 7716.7120 0.57641028 304730.00\n+ 7721.5250 0.57240859 304752.00\n+ 7726.3570 0.56757710 304652.00\n+ 7731.2080 0.56298530 304949.00\n+ 7736.0780 0.55790407 301749.00\n+ 7740.9670 0.55415072 309843.00\n+ 7745.8750 0.55025596 306494.00\n+ 7750.8030 0.54458907 306086.00\n+ 7755.7500 0.53968840 306137.00\n+ 7760.7150 0.53400917 306150.00\n+ 7765.6990 0.52848485 306231.00\n+ 7770.7030 0.52243506 306178.00\n+ 7775.7260 0.51730921 305604.00\n+ 7780.7670 0.51119667 306396.00\n+ 7785.8280 0.50502129 306122.00\n+ 7790.9080 0.49915279 306044.00\n+ 7796.0070 0.49353357 305959.00\n+ 7801.1250 0.48866156 305944.00\n+ 7806.2620 0.48323724 305753.00\n+ 7811.4180 0.47782882 305897.00\n+ 7816.5940 0.47305934 305849.00\n+ 7821.7880 0.46837192 305834.00\n+ 7827.0010 0.46392860 305216.00\n+ 7832.2340 0.45913400 306347.00\n+ 7837.4850 0.45441121 305718.00\n+ 7842.7560 0.44961359 305672.00\n+ 7848.0460 0.44433501 305591.00\n+ 7853.3540 0.43874661 305721.00\n+ 7858.6830 0.43362602 305761.00\n+ 7864.0300 0.42833655 305543.00\n+ 7869.3960 0.42287776 305580.00\n+ 7874.7810 0.41790268 305561.00\n+ 7880.1850 0.41331540 305567.00\n+ 7885.6080 0.40736809 305548.00\n+ 7891.0510 0.40162419 305485.00\n+ 7896.5120 0.39641156 305410.00\n+ 7901.9920 0.39158402 305454.00\n+ 7907.4920 0.38664929 305471.00\n+ 7913.0110 0.38183248 305389.00\n+ 7918.5480 0.37664824 305311.00\n+ 7924.1050 0.37186542 305383.00\n+ 7929.6810 0.36622348 305224.00\n+ 7935.2760 0.36059857 305309.00\n+ 7940.8900 0.35529935 304801.00\n+ 7946.5230 0.34983333 305709.00\n+ 7952.1750 0.34434706 305185.00\n+ 7957.8470 0.33897801 305134.00\n+ 7963.5370 0.33392445 305037.00\n+ 7969.2470 0.32835579 305340.00\n\\ No newline at end of file\n' |
| b |
| diff -r ae2f265ecf8e -r 2b3115342fef test-data/multiple.prj |
| b |
| Binary file test-data/multiple.prj has changed |