coxmunk 1.2.1__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
coxmunk-1.2.1/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2019-2026 Tristan Harmel
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
coxmunk-1.2.1/PKG-INFO ADDED
@@ -0,0 +1,337 @@
1
+ Metadata-Version: 2.4
2
+ Name: coxmunk
3
+ Version: 1.2.1
4
+ Summary: Sunglint (Stokes vector) computation from the Cox-Munk wave slope statistics
5
+ Author-email: "T. Harmel" <tristan.harmel@gmail.com>
6
+ License-Expression: MIT
7
+ Project-URL: Homepage, https://github.com/Tristanovsk/coxmunk
8
+ Project-URL: Documentation, https://coxmunk.readthedocs.io
9
+ Project-URL: Repository, https://github.com/Tristanovsk/coxmunk
10
+ Project-URL: Issues, https://github.com/Tristanovsk/coxmunk/issues
11
+ Keywords: sunglint,Cox-Munk,sea surface,ocean color,remote sensing,polarization,wind speed
12
+ Classifier: Development Status :: 5 - Production/Stable
13
+ Classifier: Intended Audience :: Science/Research
14
+ Classifier: Operating System :: OS Independent
15
+ Classifier: Programming Language :: Python :: 3
16
+ Classifier: Topic :: Scientific/Engineering :: Atmospheric Science
17
+ Classifier: Topic :: Scientific/Engineering :: Physics
18
+ Requires-Python: >=3.9
19
+ Description-Content-Type: text/markdown
20
+ License-File: LICENSE
21
+ Requires-Dist: numpy
22
+ Requires-Dist: scipy
23
+ Requires-Dist: pandas
24
+ Requires-Dist: xarray
25
+ Requires-Dist: netCDF4
26
+ Requires-Dist: matplotlib
27
+ Requires-Dist: cmocean
28
+ Requires-Dist: docopt
29
+ Dynamic: license-file
30
+
31
+ # coxmunk
32
+
33
+ Simple sunglint computation based on [Cox & Munk](https://www.osapublishing.org/josa/abstract.cfm?uri=josa-44-11-838) model.
34
+ The sunglint, sunlight reflected by the waves, induces different patterns at different spatial
35
+ (or temporal) scales, as in these examples:
36
+
37
+ - (a) sea surface under gust wind conditions (reflex digital camera);
38
+ - (b) aerial photograph of the sea surface with visible surfactant filaments;
39
+ - (c\) Sentinel-2A image (4 July 2015) in the 2190-nm channel, where sunglint is the most intense
40
+ signal over water; the glint highlights eddies, ship wakes and wave packets;
41
+ - (d) Sentinel-3 RGB image (10 May 2016) over the eastern Mediterranean Sea, with high sunglint on
42
+ the right side.
43
+
44
+ ![Sunglint patterns at different spatial scales](https://raw.githubusercontent.com/Tristanovsk/coxmunk/main/illustration/research/neukermans2018_fig11_sunglint_scales.jpg)
45
+
46
+ Credits: Neukermans, Harmel, Galí et al. (2018). Harnessing remote sensing to address critical
47
+ science questions on ocean-atmosphere interactions. *Elementa*, 6, 71,
48
+ [doi:10.1525/elementa.331](https://doi.org/10.1525/elementa.331) (Fig. 11, CC BY 4.0).
49
+
50
+ For more details on the statistics of the wave slopes (i.e., *Probability Distribution Function*), please refer to [Munk 2009](https://www.annualreviews.org/doi/abs/10.1146/annurev.marine.010908.163940).
51
+
52
+ ![image_output](https://raw.githubusercontent.com/Tristanovsk/coxmunk/main/illustration/sunglint_examples_sza3_optimized.gif)
53
+
54
+ ## Installation
55
+
56
+ `coxmunk` requires Python >= 3.9. Its dependencies (numpy, scipy, pandas, xarray, netCDF4,
57
+ matplotlib, cmocean, docopt) are installed automatically by `pip`.
58
+
59
+ It is best installed in a virtual environment:
60
+
61
+ ```
62
+ python3 -m venv .venv
63
+ source .venv/bin/activate # Windows: .venv\Scripts\activate
64
+ python -m pip install --upgrade pip
65
+ ```
66
+
67
+ or in a conda environment:
68
+
69
+ ```
70
+ conda create -n coxmunk python=3.12
71
+ conda activate coxmunk
72
+ ```
73
+
74
+ ### From PyPI
75
+
76
+ ```
77
+ python -m pip install coxmunk
78
+ ```
79
+
80
+ ### Development version from GitHub
81
+
82
+ The `develop` branch contains the latest changes not yet released:
83
+
84
+ ```
85
+ python -m pip install "git+https://github.com/Tristanovsk/coxmunk.git@develop"
86
+ ```
87
+
88
+ ### From source, for development
89
+
90
+ Clone [the repository](https://github.com/Tristanovsk/coxmunk) and install it in editable mode
91
+ (code changes are picked up without reinstalling):
92
+
93
+ ```
94
+ git clone https://github.com/Tristanovsk/coxmunk.git
95
+ cd coxmunk
96
+ python -m pip install -e .
97
+ ```
98
+
99
+ Run the tests with:
100
+
101
+ ```
102
+ python -m pip install pytest
103
+ python -m pytest tests
104
+ ```
105
+
106
+ and build the documentation with:
107
+
108
+ ```
109
+ python -m pip install -r docs/requirements.txt
110
+ make -C docs html # output in docs/build/html
111
+ ```
112
+
113
+ ### Check the installation
114
+
115
+ The installation provides the `coxmunk` command:
116
+
117
+ ```
118
+ $ coxmunk --version
119
+ coxmunk 1.2.1
120
+ $ coxmunk
121
+ Usage:
122
+ coxmunk <sza> <wind_speed> [--stats <stats>] [--wind_azi <wind_azi>] [--shadow] [--slope] [--figname <figname>]
123
+ coxmunk -h | --help
124
+ coxmunk -v | --version
125
+ ```
126
+
127
+ The model can also be used from Python:
128
+
129
+ ```python
130
+ from coxmunk import sunglint
131
+
132
+ # geometry in degrees: solar zenith, viewing zenith, relative azimuth (180° = Sun and sensor in opposition)
133
+ I, Q, U, V = sunglint(sza=30, vza=30, azi=180).sunglint(ws=5, wazi=0, stats='bh2006', shadow=True)
134
+ ```
135
+
136
+ The full documentation, with the API reference and tutorials, is on
137
+ [Read the Docs](https://coxmunk.readthedocs.io).
138
+
139
+ ## Model description
140
+
141
+ The sea surface is described as a collection of plane facets whose slopes follow the
142
+ statistics of Cox & Munk (1954). The glint observed in a given direction comes from the
143
+ facets tilted so that the Sun is specularly reflected toward the sensor.
144
+
145
+ ### Reflecting facet
146
+
147
+ With the solar and viewing zenith angles $\theta_s$, $\theta_v$ ($\mu = \cos\theta$) and the
148
+ relative azimuth $\phi$ (180° when Sun and sensor are in opposition), the scattering angle
149
+ $\Theta$, the angle of incidence on the facet $\omega$ and the facet tilt $\theta_n$ are
150
+
151
+ ```math
152
+ \cos\Theta = -\mu_s\mu_v - \sin\theta_s\sin\theta_v\cos\phi, \qquad
153
+ \omega = \frac{\pi - \Theta}{2}, \qquad
154
+ \cos\theta_n = \frac{\mu_s + \mu_v}{2\cos\omega}
155
+ ```
156
+
157
+ The facet slopes are computed in the Sun frame and rotated into the wind frame, with
158
+ $\phi_w$ the downwind direction counted counterclockwise from the Sun:
159
+
160
+ ```math
161
+ z_x = -\frac{\sin\theta_v \cos\phi + \sin\theta_s}{\mu_s + \mu_v}, \quad
162
+ z_y = -\frac{\sin\theta_v \sin\phi}{\mu_s + \mu_v}, \quad
163
+ z_{up} = \cos\phi_w \, z_x + \sin\phi_w \, z_y, \quad
164
+ z_{cr} = -\sin\phi_w \, z_x + \cos\phi_w \, z_y
165
+ ```
166
+
167
+ ### Wave slope statistics
168
+
169
+ For the isotropic statistics (`cm_iso`), with the wind speed $U$ in m/s:
170
+
171
+ ```math
172
+ \sigma^2 = 0.003 + 5.12\times10^{-3}\,U, \qquad
173
+ P = \frac{1}{\pi\sigma^2} \exp\left(-\frac{\tan^2\theta_n}{\sigma^2}\right)
174
+ ```
175
+
176
+ For the anisotropic statistics (`cm_dir`, `bh2006`), the Gram-Charlier expansion is written
177
+ with the convention of Munk (2009), with $\xi = z_{up}/\sigma_{up}$ and $\eta = z_{cr}/\sigma_{cr}$:
178
+
179
+ ```math
180
+ P(\xi, \eta) = \frac{e^{-(\xi^2 + \eta^2)/2}}{2\pi\,\sigma_{up}\,\sigma_{cr}}
181
+ \Big[ 1
182
+ + \tfrac{c_{12}}{2}\,\xi\,(1 - \eta^2)
183
+ - \tfrac{c_{30}}{6}\,\xi\,(3 - \xi^2)
184
+ + \tfrac{c_{40}}{24}\,(3 - 6\xi^2 + \xi^4)
185
+ + \tfrac{c_{22}}{4}\,(1 - \xi^2)(1 - \eta^2)
186
+ + \tfrac{c_{04}}{24}\,(3 - 6\eta^2 + \eta^4)
187
+ \Big]
188
+ ```
189
+
190
+ where $c_{12} = -c_{21}$ and $c_{30} = -c_{03}$, with the coefficients:
191
+
192
+ | Parameter | `cm_dir` (Cox & Munk, 1954) | `bh2006` (Bréon & Henriot, 2006) |
193
+ |---|---|---|
194
+ | $\sigma_{cr}^2$ | $0.003 + 1.92\times10^{-3}\,U$ | $0.003 + 1.85\times10^{-3}\,U$ |
195
+ | $\sigma_{up}^2$ | $3.16\times10^{-3}\,U$ | $0.001 + 3.16\times10^{-3}\,U$ |
196
+ | $c_{21}$ | $0.01 - 8.6\times10^{-3}\,U$ | $-9\times10^{-4}\,U^2$ |
197
+ | $c_{03}$ | $0.04 - 0.033\,U$ | $-0.45 / (1 + e^{7 - U})$ |
198
+ | $c_{40}$ | 0.40 | 0.30 |
199
+ | $c_{22}$ | 0.12 | 0.12 |
200
+ | $c_{04}$ | 0.23 | 0.40 |
201
+
202
+ ### Fresnel reflection
203
+
204
+ With the refractive index of water $m$ (default 1.334), the reflection coefficients
205
+ parallel and perpendicular to the plane of incidence are
206
+
207
+ ```math
208
+ r_l = \frac{\sqrt{m^2 - \sin^2\omega} - m^2\cos\omega}{\sqrt{m^2 - \sin^2\omega} + m^2\cos\omega},
209
+ \qquad
210
+ r_r = \frac{\cos\omega - \sqrt{m^2 - \sin^2\omega}}{\cos\omega + \sqrt{m^2 - \sin^2\omega}}
211
+ ```
212
+
213
+ giving the Mueller reflection matrix
214
+
215
+ ```math
216
+ \mathbf{R}_F(\omega) = \frac{1}{2}
217
+ \begin{pmatrix}
218
+ r_l^2 + r_r^2 & r_l^2 - r_r^2 & 0 & 0 \\
219
+ r_l^2 - r_r^2 & r_l^2 + r_r^2 & 0 & 0 \\
220
+ 0 & 0 & 2 r_l r_r & 0 \\
221
+ 0 & 0 & 0 & 2 r_l r_r
222
+ \end{pmatrix}
223
+ ```
224
+
225
+ which is rotated from the meridian planes into the scattering plane,
226
+ $\mathbf{R} = \mathbf{L}(\pi - \sigma_2)\,\mathbf{R}_F\,\mathbf{L}(-\sigma_1)$.
227
+
228
+ ### Shadowing and hiding
229
+
230
+ With `--shadow` (`shadow=True` in Python), the facets hidden by the waves are removed
231
+ with the Smith function (Ross & Dion, 2005, 2007):
232
+
233
+ ```math
234
+ \Lambda(\theta, \varphi) = \frac{e^{-\nu^2} - \nu\sqrt{\pi}\,\mathrm{erfc}(\nu)}{2\,\nu\sqrt{\pi}},
235
+ \qquad
236
+ \nu = \frac{1}{\sqrt{2}\,\sigma(\varphi)\tan\theta},
237
+ \qquad
238
+ \sigma^2(\varphi) = \sigma_{up}^2\cos^2\varphi + \sigma_{cr}^2\sin^2\varphi
239
+ ```
240
+
241
+ ```math
242
+ SH = \frac{1}{1 + \Lambda(\theta_s, -\phi_w) + \Lambda(\theta_v, \phi - \phi_w)}
243
+ ```
244
+
245
+ where $\varphi$ is the azimuth of the direction relative to the upwind axis.
246
+
247
+ ### Sunglint Stokes vector
248
+
249
+ The sunglint, in reflectance units, is finally
250
+
251
+ ```math
252
+ \begin{pmatrix} I \\ Q \\ U \\ V \end{pmatrix}
253
+ = \frac{\pi \, P \, SH}{4 \, \mu_s \, \mu_v \cos^4\theta_n}
254
+ \begin{pmatrix} R_{11} \\ R_{21} \\ R_{31} \\ R_{41} \end{pmatrix}
255
+ ```
256
+
257
+ ### References
258
+
259
+ - Cox, C. and Munk, W. (1954). Measurement of the roughness of the sea surface from photographs of the Sun's glitter. *J. Opt. Soc. Am.*, 44(11), 838-850.
260
+ - Bréon, F.-M. and Henriot, N. (2006). Spaceborne observations of ocean glint reflectance and modeling of wave slope distributions. *J. Geophys. Res.*, 111, C06005.
261
+ - Munk, W. (2009). An inconvenient sea truth: spread, steepness, and skewness of surface slopes. *Annu. Rev. Mar. Sci.*, 1, 377-415.
262
+ - Ross, V., Dion, D. and Potvin, G. (2005). Detailed analytical approach to the Gaussian surface bidirectional reflectance distribution function specular component applied to the sea surface. *J. Opt. Soc. Am. A*, 22(11), 2442-2453.
263
+ - Harmel, T. and Chami, M. (2012). Determination of sea surface wind speed using the polarimetric and multidirectional properties of satellite measurements in visible bands. *Geophys. Res. Lett.*, 39, L19611, doi:10.1029/2012GL053508.
264
+ - Harmel, T. and Chami, M. (2013). Estimation of the sunglint radiance field from optical satellite imagery over open ocean: multidirectional approach and polarization aspects. *J. Geophys. Res. Oceans*, 118, doi:10.1029/2012JC008221.
265
+ - Ross, V. and Dion, D. (2007). Sea surface slope statistics derived from Sun glint radiance measurements and their apparent dependence on sensor elevation. *J. Geophys. Res.*, 112, C09015.
266
+
267
+ ## Polarization and wind speed retrieval
268
+
269
+ Since the polarization of the glint only depends on the geometry while its amount depends on the
270
+ sea state, multidirectional and polarized measurements (e.g., POLDER/PARASOL) can be used to
271
+ retrieve the sunglint Stokes vector (Harmel & Chami, 2013) and the sea surface wind speed
272
+ (Harmel & Chami, 2012). The `coxmunk.wind` module implements the forward model (sunglint plus
273
+ whitecaps) and the Levenberg-Marquardt inversion of Harmel & Chami (2012):
274
+
275
+ ```python
276
+ import numpy as np
277
+ from coxmunk.wind import glint_whitecap, retrieve_wind_speed
278
+
279
+ # 14 viewing directions along a satellite track: (sza, vza, azi) in degrees
280
+ geometries = np.array([(30, abs(v), 150 if v >= 0 else 330) for v in np.linspace(-55, 55, 14)])
281
+ observed = glint_whitecap(geometries, ws=8) # synthetic I, Q, U measurements
282
+ res = retrieve_wind_speed(observed, geometries) # -> res.ws, res.sigma, res.flag
283
+ ```
284
+
285
+ See the [polarization](https://coxmunk.readthedocs.io/en/latest/polarization.html) and
286
+ [wind speed](https://coxmunk.readthedocs.io/en/latest/wind_speed.html) chapters of the documentation.
287
+
288
+ ## Kumatage: from noise to signal
289
+
290
+ ![Spooner 1822](https://raw.githubusercontent.com/Tristanovsk/coxmunk/main/illustration/kumatage/spooner_1822_lettre_IV.jpg)
291
+
292
+ In 1822, Spooner named *Kumatage* (from the Greek κυμάτων, *of the waves*, and αὐγή, *splendour*)
293
+ "this remarkable appearance of light" of the Sun reflected by the waves, and established its first
294
+ equations. Navigators filtered it out as a glare, painters made it a subject, Cox & Munk turned it
295
+ into a measurement of the sea surface slopes, ocean color remote sensing removed it as a noise, and
296
+ it is now exploited as a signal on winds, waves, currents and slicks. The
297
+ [History section](https://coxmunk.readthedocs.io/en/latest/history/kumatage.html) of the documentation
298
+ retraces this history (adapted from Harmel, Bary, Gernez & Morin, OCEANEXT 2019), with paintings,
299
+ Cox & Munk and Sentinel-2 images.
300
+
301
+ ## Examples
302
+
303
+ Examples for [Cox & Munk](https://www.osapublishing.org/josa/abstract.cfm?uri=josa-44-11-838) model with [Bréon & Henriot](https://agupubs.onlinelibrary.wiley.com/doi/full/10.1029/2005JC003343) statistics for:
304
+ - solar zenith angle = 39°
305
+ - wind azimuth from Sun = 75°
306
+ - wind speed = 0.2, 7.2, 14.2 m.s<sup>-1</sup>
307
+
308
+ ```
309
+ $ coxmunk 39 0.2 --stats bh2006 --wind_azi 75 --figname illustration/coxmunk_fig_39_0.2_bh2006_75.png
310
+ ```
311
+
312
+ ![image_output](https://raw.githubusercontent.com/Tristanovsk/coxmunk/main/illustration/coxmunk_fig_39_0.2_bh2006_75.png)
313
+
314
+
315
+ ```
316
+ $ coxmunk 39 7.2 --stats bh2006 --wind_azi 75
317
+ ```
318
+
319
+ ![image_output](https://raw.githubusercontent.com/Tristanovsk/coxmunk/main/illustration/coxmunk_fig_39_7.2_bh2006_75.png)
320
+
321
+
322
+
323
+ ```
324
+ $ coxmunk 39 14.2 --stats bh2006 --wind_azi 75
325
+ ```
326
+
327
+ ![image_output](https://raw.githubusercontent.com/Tristanovsk/coxmunk/main/illustration/coxmunk_fig_39_14.2_bh2006_75.png)
328
+
329
+ With the option `--slope` you can also check
330
+ the values of wave slopes upwind and crosswind,
331
+ the first term of the Fresnel matrix and the probability distribution function:
332
+
333
+ ```
334
+ $ coxmunk 20 5 --stats bh2006 --wind_azi 60 --slope
335
+ ```
336
+
337
+ ![image_output](https://raw.githubusercontent.com/Tristanovsk/coxmunk/main/illustration/coxmunk_fig_sza20_ws5_wazi60_bh2006--slope.png)
@@ -0,0 +1,307 @@
1
+ # coxmunk
2
+
3
+ Simple sunglint computation based on [Cox & Munk](https://www.osapublishing.org/josa/abstract.cfm?uri=josa-44-11-838) model.
4
+ The sunglint, sunlight reflected by the waves, induces different patterns at different spatial
5
+ (or temporal) scales, as in these examples:
6
+
7
+ - (a) sea surface under gust wind conditions (reflex digital camera);
8
+ - (b) aerial photograph of the sea surface with visible surfactant filaments;
9
+ - (c\) Sentinel-2A image (4 July 2015) in the 2190-nm channel, where sunglint is the most intense
10
+ signal over water; the glint highlights eddies, ship wakes and wave packets;
11
+ - (d) Sentinel-3 RGB image (10 May 2016) over the eastern Mediterranean Sea, with high sunglint on
12
+ the right side.
13
+
14
+ ![Sunglint patterns at different spatial scales](https://raw.githubusercontent.com/Tristanovsk/coxmunk/main/illustration/research/neukermans2018_fig11_sunglint_scales.jpg)
15
+
16
+ Credits: Neukermans, Harmel, Galí et al. (2018). Harnessing remote sensing to address critical
17
+ science questions on ocean-atmosphere interactions. *Elementa*, 6, 71,
18
+ [doi:10.1525/elementa.331](https://doi.org/10.1525/elementa.331) (Fig. 11, CC BY 4.0).
19
+
20
+ For more details on the statistics of the wave slopes (i.e., *Probability Distribution Function*), please refer to [Munk 2009](https://www.annualreviews.org/doi/abs/10.1146/annurev.marine.010908.163940).
21
+
22
+ ![image_output](https://raw.githubusercontent.com/Tristanovsk/coxmunk/main/illustration/sunglint_examples_sza3_optimized.gif)
23
+
24
+ ## Installation
25
+
26
+ `coxmunk` requires Python >= 3.9. Its dependencies (numpy, scipy, pandas, xarray, netCDF4,
27
+ matplotlib, cmocean, docopt) are installed automatically by `pip`.
28
+
29
+ It is best installed in a virtual environment:
30
+
31
+ ```
32
+ python3 -m venv .venv
33
+ source .venv/bin/activate # Windows: .venv\Scripts\activate
34
+ python -m pip install --upgrade pip
35
+ ```
36
+
37
+ or in a conda environment:
38
+
39
+ ```
40
+ conda create -n coxmunk python=3.12
41
+ conda activate coxmunk
42
+ ```
43
+
44
+ ### From PyPI
45
+
46
+ ```
47
+ python -m pip install coxmunk
48
+ ```
49
+
50
+ ### Development version from GitHub
51
+
52
+ The `develop` branch contains the latest changes not yet released:
53
+
54
+ ```
55
+ python -m pip install "git+https://github.com/Tristanovsk/coxmunk.git@develop"
56
+ ```
57
+
58
+ ### From source, for development
59
+
60
+ Clone [the repository](https://github.com/Tristanovsk/coxmunk) and install it in editable mode
61
+ (code changes are picked up without reinstalling):
62
+
63
+ ```
64
+ git clone https://github.com/Tristanovsk/coxmunk.git
65
+ cd coxmunk
66
+ python -m pip install -e .
67
+ ```
68
+
69
+ Run the tests with:
70
+
71
+ ```
72
+ python -m pip install pytest
73
+ python -m pytest tests
74
+ ```
75
+
76
+ and build the documentation with:
77
+
78
+ ```
79
+ python -m pip install -r docs/requirements.txt
80
+ make -C docs html # output in docs/build/html
81
+ ```
82
+
83
+ ### Check the installation
84
+
85
+ The installation provides the `coxmunk` command:
86
+
87
+ ```
88
+ $ coxmunk --version
89
+ coxmunk 1.2.1
90
+ $ coxmunk
91
+ Usage:
92
+ coxmunk <sza> <wind_speed> [--stats <stats>] [--wind_azi <wind_azi>] [--shadow] [--slope] [--figname <figname>]
93
+ coxmunk -h | --help
94
+ coxmunk -v | --version
95
+ ```
96
+
97
+ The model can also be used from Python:
98
+
99
+ ```python
100
+ from coxmunk import sunglint
101
+
102
+ # geometry in degrees: solar zenith, viewing zenith, relative azimuth (180° = Sun and sensor in opposition)
103
+ I, Q, U, V = sunglint(sza=30, vza=30, azi=180).sunglint(ws=5, wazi=0, stats='bh2006', shadow=True)
104
+ ```
105
+
106
+ The full documentation, with the API reference and tutorials, is on
107
+ [Read the Docs](https://coxmunk.readthedocs.io).
108
+
109
+ ## Model description
110
+
111
+ The sea surface is described as a collection of plane facets whose slopes follow the
112
+ statistics of Cox & Munk (1954). The glint observed in a given direction comes from the
113
+ facets tilted so that the Sun is specularly reflected toward the sensor.
114
+
115
+ ### Reflecting facet
116
+
117
+ With the solar and viewing zenith angles $\theta_s$, $\theta_v$ ($\mu = \cos\theta$) and the
118
+ relative azimuth $\phi$ (180° when Sun and sensor are in opposition), the scattering angle
119
+ $\Theta$, the angle of incidence on the facet $\omega$ and the facet tilt $\theta_n$ are
120
+
121
+ ```math
122
+ \cos\Theta = -\mu_s\mu_v - \sin\theta_s\sin\theta_v\cos\phi, \qquad
123
+ \omega = \frac{\pi - \Theta}{2}, \qquad
124
+ \cos\theta_n = \frac{\mu_s + \mu_v}{2\cos\omega}
125
+ ```
126
+
127
+ The facet slopes are computed in the Sun frame and rotated into the wind frame, with
128
+ $\phi_w$ the downwind direction counted counterclockwise from the Sun:
129
+
130
+ ```math
131
+ z_x = -\frac{\sin\theta_v \cos\phi + \sin\theta_s}{\mu_s + \mu_v}, \quad
132
+ z_y = -\frac{\sin\theta_v \sin\phi}{\mu_s + \mu_v}, \quad
133
+ z_{up} = \cos\phi_w \, z_x + \sin\phi_w \, z_y, \quad
134
+ z_{cr} = -\sin\phi_w \, z_x + \cos\phi_w \, z_y
135
+ ```
136
+
137
+ ### Wave slope statistics
138
+
139
+ For the isotropic statistics (`cm_iso`), with the wind speed $U$ in m/s:
140
+
141
+ ```math
142
+ \sigma^2 = 0.003 + 5.12\times10^{-3}\,U, \qquad
143
+ P = \frac{1}{\pi\sigma^2} \exp\left(-\frac{\tan^2\theta_n}{\sigma^2}\right)
144
+ ```
145
+
146
+ For the anisotropic statistics (`cm_dir`, `bh2006`), the Gram-Charlier expansion is written
147
+ with the convention of Munk (2009), with $\xi = z_{up}/\sigma_{up}$ and $\eta = z_{cr}/\sigma_{cr}$:
148
+
149
+ ```math
150
+ P(\xi, \eta) = \frac{e^{-(\xi^2 + \eta^2)/2}}{2\pi\,\sigma_{up}\,\sigma_{cr}}
151
+ \Big[ 1
152
+ + \tfrac{c_{12}}{2}\,\xi\,(1 - \eta^2)
153
+ - \tfrac{c_{30}}{6}\,\xi\,(3 - \xi^2)
154
+ + \tfrac{c_{40}}{24}\,(3 - 6\xi^2 + \xi^4)
155
+ + \tfrac{c_{22}}{4}\,(1 - \xi^2)(1 - \eta^2)
156
+ + \tfrac{c_{04}}{24}\,(3 - 6\eta^2 + \eta^4)
157
+ \Big]
158
+ ```
159
+
160
+ where $c_{12} = -c_{21}$ and $c_{30} = -c_{03}$, with the coefficients:
161
+
162
+ | Parameter | `cm_dir` (Cox & Munk, 1954) | `bh2006` (Bréon & Henriot, 2006) |
163
+ |---|---|---|
164
+ | $\sigma_{cr}^2$ | $0.003 + 1.92\times10^{-3}\,U$ | $0.003 + 1.85\times10^{-3}\,U$ |
165
+ | $\sigma_{up}^2$ | $3.16\times10^{-3}\,U$ | $0.001 + 3.16\times10^{-3}\,U$ |
166
+ | $c_{21}$ | $0.01 - 8.6\times10^{-3}\,U$ | $-9\times10^{-4}\,U^2$ |
167
+ | $c_{03}$ | $0.04 - 0.033\,U$ | $-0.45 / (1 + e^{7 - U})$ |
168
+ | $c_{40}$ | 0.40 | 0.30 |
169
+ | $c_{22}$ | 0.12 | 0.12 |
170
+ | $c_{04}$ | 0.23 | 0.40 |
171
+
172
+ ### Fresnel reflection
173
+
174
+ With the refractive index of water $m$ (default 1.334), the reflection coefficients
175
+ parallel and perpendicular to the plane of incidence are
176
+
177
+ ```math
178
+ r_l = \frac{\sqrt{m^2 - \sin^2\omega} - m^2\cos\omega}{\sqrt{m^2 - \sin^2\omega} + m^2\cos\omega},
179
+ \qquad
180
+ r_r = \frac{\cos\omega - \sqrt{m^2 - \sin^2\omega}}{\cos\omega + \sqrt{m^2 - \sin^2\omega}}
181
+ ```
182
+
183
+ giving the Mueller reflection matrix
184
+
185
+ ```math
186
+ \mathbf{R}_F(\omega) = \frac{1}{2}
187
+ \begin{pmatrix}
188
+ r_l^2 + r_r^2 & r_l^2 - r_r^2 & 0 & 0 \\
189
+ r_l^2 - r_r^2 & r_l^2 + r_r^2 & 0 & 0 \\
190
+ 0 & 0 & 2 r_l r_r & 0 \\
191
+ 0 & 0 & 0 & 2 r_l r_r
192
+ \end{pmatrix}
193
+ ```
194
+
195
+ which is rotated from the meridian planes into the scattering plane,
196
+ $\mathbf{R} = \mathbf{L}(\pi - \sigma_2)\,\mathbf{R}_F\,\mathbf{L}(-\sigma_1)$.
197
+
198
+ ### Shadowing and hiding
199
+
200
+ With `--shadow` (`shadow=True` in Python), the facets hidden by the waves are removed
201
+ with the Smith function (Ross & Dion, 2005, 2007):
202
+
203
+ ```math
204
+ \Lambda(\theta, \varphi) = \frac{e^{-\nu^2} - \nu\sqrt{\pi}\,\mathrm{erfc}(\nu)}{2\,\nu\sqrt{\pi}},
205
+ \qquad
206
+ \nu = \frac{1}{\sqrt{2}\,\sigma(\varphi)\tan\theta},
207
+ \qquad
208
+ \sigma^2(\varphi) = \sigma_{up}^2\cos^2\varphi + \sigma_{cr}^2\sin^2\varphi
209
+ ```
210
+
211
+ ```math
212
+ SH = \frac{1}{1 + \Lambda(\theta_s, -\phi_w) + \Lambda(\theta_v, \phi - \phi_w)}
213
+ ```
214
+
215
+ where $\varphi$ is the azimuth of the direction relative to the upwind axis.
216
+
217
+ ### Sunglint Stokes vector
218
+
219
+ The sunglint, in reflectance units, is finally
220
+
221
+ ```math
222
+ \begin{pmatrix} I \\ Q \\ U \\ V \end{pmatrix}
223
+ = \frac{\pi \, P \, SH}{4 \, \mu_s \, \mu_v \cos^4\theta_n}
224
+ \begin{pmatrix} R_{11} \\ R_{21} \\ R_{31} \\ R_{41} \end{pmatrix}
225
+ ```
226
+
227
+ ### References
228
+
229
+ - Cox, C. and Munk, W. (1954). Measurement of the roughness of the sea surface from photographs of the Sun's glitter. *J. Opt. Soc. Am.*, 44(11), 838-850.
230
+ - Bréon, F.-M. and Henriot, N. (2006). Spaceborne observations of ocean glint reflectance and modeling of wave slope distributions. *J. Geophys. Res.*, 111, C06005.
231
+ - Munk, W. (2009). An inconvenient sea truth: spread, steepness, and skewness of surface slopes. *Annu. Rev. Mar. Sci.*, 1, 377-415.
232
+ - Ross, V., Dion, D. and Potvin, G. (2005). Detailed analytical approach to the Gaussian surface bidirectional reflectance distribution function specular component applied to the sea surface. *J. Opt. Soc. Am. A*, 22(11), 2442-2453.
233
+ - Harmel, T. and Chami, M. (2012). Determination of sea surface wind speed using the polarimetric and multidirectional properties of satellite measurements in visible bands. *Geophys. Res. Lett.*, 39, L19611, doi:10.1029/2012GL053508.
234
+ - Harmel, T. and Chami, M. (2013). Estimation of the sunglint radiance field from optical satellite imagery over open ocean: multidirectional approach and polarization aspects. *J. Geophys. Res. Oceans*, 118, doi:10.1029/2012JC008221.
235
+ - Ross, V. and Dion, D. (2007). Sea surface slope statistics derived from Sun glint radiance measurements and their apparent dependence on sensor elevation. *J. Geophys. Res.*, 112, C09015.
236
+
237
+ ## Polarization and wind speed retrieval
238
+
239
+ Since the polarization of the glint only depends on the geometry while its amount depends on the
240
+ sea state, multidirectional and polarized measurements (e.g., POLDER/PARASOL) can be used to
241
+ retrieve the sunglint Stokes vector (Harmel & Chami, 2013) and the sea surface wind speed
242
+ (Harmel & Chami, 2012). The `coxmunk.wind` module implements the forward model (sunglint plus
243
+ whitecaps) and the Levenberg-Marquardt inversion of Harmel & Chami (2012):
244
+
245
+ ```python
246
+ import numpy as np
247
+ from coxmunk.wind import glint_whitecap, retrieve_wind_speed
248
+
249
+ # 14 viewing directions along a satellite track: (sza, vza, azi) in degrees
250
+ geometries = np.array([(30, abs(v), 150 if v >= 0 else 330) for v in np.linspace(-55, 55, 14)])
251
+ observed = glint_whitecap(geometries, ws=8) # synthetic I, Q, U measurements
252
+ res = retrieve_wind_speed(observed, geometries) # -> res.ws, res.sigma, res.flag
253
+ ```
254
+
255
+ See the [polarization](https://coxmunk.readthedocs.io/en/latest/polarization.html) and
256
+ [wind speed](https://coxmunk.readthedocs.io/en/latest/wind_speed.html) chapters of the documentation.
257
+
258
+ ## Kumatage: from noise to signal
259
+
260
+ ![Spooner 1822](https://raw.githubusercontent.com/Tristanovsk/coxmunk/main/illustration/kumatage/spooner_1822_lettre_IV.jpg)
261
+
262
+ In 1822, Spooner named *Kumatage* (from the Greek κυμάτων, *of the waves*, and αὐγή, *splendour*)
263
+ "this remarkable appearance of light" of the Sun reflected by the waves, and established its first
264
+ equations. Navigators filtered it out as a glare, painters made it a subject, Cox & Munk turned it
265
+ into a measurement of the sea surface slopes, ocean color remote sensing removed it as a noise, and
266
+ it is now exploited as a signal on winds, waves, currents and slicks. The
267
+ [History section](https://coxmunk.readthedocs.io/en/latest/history/kumatage.html) of the documentation
268
+ retraces this history (adapted from Harmel, Bary, Gernez & Morin, OCEANEXT 2019), with paintings,
269
+ Cox & Munk and Sentinel-2 images.
270
+
271
+ ## Examples
272
+
273
+ Examples for [Cox & Munk](https://www.osapublishing.org/josa/abstract.cfm?uri=josa-44-11-838) model with [Bréon & Henriot](https://agupubs.onlinelibrary.wiley.com/doi/full/10.1029/2005JC003343) statistics for:
274
+ - solar zenith angle = 39°
275
+ - wind azimuth from Sun = 75°
276
+ - wind speed = 0.2, 7.2, 14.2 m.s<sup>-1</sup>
277
+
278
+ ```
279
+ $ coxmunk 39 0.2 --stats bh2006 --wind_azi 75 --figname illustration/coxmunk_fig_39_0.2_bh2006_75.png
280
+ ```
281
+
282
+ ![image_output](https://raw.githubusercontent.com/Tristanovsk/coxmunk/main/illustration/coxmunk_fig_39_0.2_bh2006_75.png)
283
+
284
+
285
+ ```
286
+ $ coxmunk 39 7.2 --stats bh2006 --wind_azi 75
287
+ ```
288
+
289
+ ![image_output](https://raw.githubusercontent.com/Tristanovsk/coxmunk/main/illustration/coxmunk_fig_39_7.2_bh2006_75.png)
290
+
291
+
292
+
293
+ ```
294
+ $ coxmunk 39 14.2 --stats bh2006 --wind_azi 75
295
+ ```
296
+
297
+ ![image_output](https://raw.githubusercontent.com/Tristanovsk/coxmunk/main/illustration/coxmunk_fig_39_14.2_bh2006_75.png)
298
+
299
+ With the option `--slope` you can also check
300
+ the values of wave slopes upwind and crosswind,
301
+ the first term of the Fresnel matrix and the probability distribution function:
302
+
303
+ ```
304
+ $ coxmunk 20 5 --stats bh2006 --wind_azi 60 --slope
305
+ ```
306
+
307
+ ![image_output](https://raw.githubusercontent.com/Tristanovsk/coxmunk/main/illustration/coxmunk_fig_sza20_ws5_wazi60_bh2006--slope.png)
@@ -0,0 +1,7 @@
1
+
2
+ __package__ = 'coxmunk'
3
+ __version__ = '1.2.1'
4
+
5
+ from .coxmunk import sunglint
6
+ from .visu import plot
7
+ from .wind import whitecap_coverage, glint_whitecap, retrieve_wind_speed, glint_directions