@@ -106,6 +106,84 @@ selected directory and plot resulting :math:`R_w` values from each morph.
106106 PDFs. See the ``--save-names-file `` option to see how you can set
107107 the names for these saved morphs!
108108
109+ Polynomial Squeeze Morph
110+ =========================
111+
112+ Another advanced feature in ``diffpy.morph `` is the ``MorphSqueeze `` morph,
113+ which applies a user-defined polynomial to squeeze the morph function along the
114+ x-axis. This provides a flexible way to correct for higher-order distortions
115+ that simple shift or stretch morphs cannot fully address.
116+ Such distortions can arise from geometric artifacts in X-ray detector modules,
117+ including tilts, curved detection planes, or angle-dependent offsets, as well
118+ as from intrinsic structural effects in the sample.
119+
120+ A first-order squeeze polynomial recovers the behavior of simple shift or stretch,
121+ while higher-order terms enable non-linear corrections. The squeeze transformation
122+ is defined as:
123+
124+ .. math ::
125+
126+ \Delta r(r) = a_0 + a_1 r + a_2 r^2 + \dots + a_n r^n
127+
128+ where :math: `a_0 , a_1 , ..., a_n` are the polynomial coefficients defined by the user.
129+
130+ In this example, we show how to apply a squeeze morph in combination
131+ with a scale morph to match a morph function to its target. The required
132+ files can be found in ``additionalData/morphsqueeze/ ``.
133+
134+ 1. ``cd `` into the ``morphsqueeze `` directory::
135+
136+ cd additionalData/morphsqueeze
137+
138+ Here you will find:
139+
140+ - ``squeeze_morph.cgr`` — the morph function with a small built-in polynomial distortion.
141+ - ``squeeze_target.cgr`` — the target function.
142+
143+ 2. Suppose we know that the morph needs a quadratic and cubic squeeze,
144+ plus a scale factor to best match the target. As an initial guess,
145+ we can use:
146+
147+ - ``squeeze = 0,-0.001,-0.0001,0.0001 ``
148+ (for a polynomial: :math: `a_0 + a_1 x + a_2 x^2 + a_3 x^3 `)
149+ - ``scale = 1.1 ``
150+
151+ The squeeze polynomial is provided as a comma-separated list (no spaces)::
152+
153+ diffpy.morph --scale=1.1 --squeeze=0,-0.001,-0.0001,0.0001 -a squeeze_morph.cgr squeeze_target.cgr
154+
155+ 3. ``diffpy.morph `` will apply the polynomial squeeze and scale,
156+ display the initial and refined coefficients, and show the final
157+ difference ``Rw ``.
158+
159+ To refine the squeeze polynomial and scale automatically, remove
160+ the ``-a `` tag if you used it. For example::
161+
162+ diffpy.morph --scale=1.1 --squeeze=0,-0.001,-0.0001,0.0001 squeeze_morph.cgr squeeze_target.cgr
163+
164+ 4. Check the output for the final squeeze polynomial coefficients and scale.
165+ They should match the true values used to generate the test data:
166+
167+ - ``squeeze = 0, 0.01, 0.0001, 0.001 ``
168+ - ``scale = 0.5 ``
169+
170+ ``diffpy.morph `` refines the coefficients to minimize the residual
171+ between the squeezed, scaled morph function and the target.
172+
173+ .. warning ::
174+
175+ **Extrapolation risk: **
176+ A polynomial squeeze can shift morph data outside the target’s ``r ``-range,
177+ so parts of the output may be extrapolated.
178+ This is generally fine if the polynomial coefficients are small and
179+ the distortion is therefore small. If your coefficients are large, check the
180+ plots carefully — strong extrapolation can produce unrealistic features at
181+ the edges. If needed, adjust the coefficients to keep the morph physically
182+ meaningful.
183+
184+ Experiment with your own squeeze polynomials to fine-tune your morphs — even
185+ small higher-order corrections can make a big difference!
186+
109187Nanoparticle Shape Effects
110188==========================
111189
0 commit comments