microeye 2.3.2__py3-none-any.whl

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.
Files changed (190) hide show
  1. microEye/__init__.py +47 -0
  2. microEye/_version.py +2 -0
  3. microEye/analysis/__init__.py +1 -0
  4. microEye/analysis/checklist_dialog.py +143 -0
  5. microEye/analysis/cmosMaps.py +228 -0
  6. microEye/analysis/filters/__init__.py +9 -0
  7. microEye/analysis/filters/base.py +21 -0
  8. microEye/analysis/filters/spatial.py +338 -0
  9. microEye/analysis/filters/temporal.py +76 -0
  10. microEye/analysis/fitting/__init__.py +0 -0
  11. microEye/analysis/fitting/fit.py +680 -0
  12. microEye/analysis/fitting/nena.py +375 -0
  13. microEye/analysis/fitting/phasor_fit.py +90 -0
  14. microEye/analysis/fitting/processing.py +317 -0
  15. microEye/analysis/fitting/psf/__init__.py +6 -0
  16. microEye/analysis/fitting/psf/extract.py +1129 -0
  17. microEye/analysis/fitting/psf/rubost_mean.py +150 -0
  18. microEye/analysis/fitting/psf/spline.py +167 -0
  19. microEye/analysis/fitting/psf/stats/__init__.py +12 -0
  20. microEye/analysis/fitting/psf/stats/core.py +295 -0
  21. microEye/analysis/fitting/psf/stats/curve_fit.py +708 -0
  22. microEye/analysis/fitting/psf/stats/io.py +104 -0
  23. microEye/analysis/fitting/psf/stats/slope_fit.py +171 -0
  24. microEye/analysis/fitting/psf/temp.py +147 -0
  25. microEye/analysis/fitting/psf/test.py +47 -0
  26. microEye/analysis/fitting/pyfit3Dcspline/CPU/CPUfunctions.py +657 -0
  27. microEye/analysis/fitting/pyfit3Dcspline/CPU/CPUmleFit_LM.py +1336 -0
  28. microEye/analysis/fitting/pyfit3Dcspline/CPU/CPUsplineLib.py +270 -0
  29. microEye/analysis/fitting/pyfit3Dcspline/CPU/__init__.py +1 -0
  30. microEye/analysis/fitting/pyfit3Dcspline/GPU/GPUfunctions.py +609 -0
  31. microEye/analysis/fitting/pyfit3Dcspline/GPU/GPUmleFit_LM_EMCCD.py +1396 -0
  32. microEye/analysis/fitting/pyfit3Dcspline/GPU/GPUmleFit_LM_sCMOS.py +1426 -0
  33. microEye/analysis/fitting/pyfit3Dcspline/GPU/GPUsplineLib.py +231 -0
  34. microEye/analysis/fitting/pyfit3Dcspline/GPU/__init__.py +2 -0
  35. microEye/analysis/fitting/pyfit3Dcspline/__init__.py +10 -0
  36. microEye/analysis/fitting/pyfit3Dcspline/constants.py +27 -0
  37. microEye/analysis/fitting/pyfit3Dcspline/mainfunctions.py +903 -0
  38. microEye/analysis/fitting/results.py +917 -0
  39. microEye/analysis/fitting/results_stats.py +251 -0
  40. microEye/analysis/fitting/tardis.py +209 -0
  41. microEye/analysis/multi_viewer.py +568 -0
  42. microEye/analysis/processing/__init__.py +1 -0
  43. microEye/analysis/processing/frc.py +120 -0
  44. microEye/analysis/rendering/__init__.py +3 -0
  45. microEye/analysis/rendering/base.py +452 -0
  46. microEye/analysis/rendering/cloud.py +215 -0
  47. microEye/analysis/rendering/core.py +47 -0
  48. microEye/analysis/rendering/volumetric.py +198 -0
  49. microEye/analysis/tools/__init__.py +0 -0
  50. microEye/analysis/tools/kymograms.py +1079 -0
  51. microEye/analysis/tools/roi_selectors.py +556 -0
  52. microEye/analysis/utils/__init__.py +3 -0
  53. microEye/analysis/utils/coordinates.py +18 -0
  54. microEye/analysis/utils/images.py +68 -0
  55. microEye/analysis/utils/windows.py +19 -0
  56. microEye/analysis/viewer/__init__.py +3 -0
  57. microEye/analysis/viewer/image_options_widget.py +615 -0
  58. microEye/analysis/viewer/images.py +1225 -0
  59. microEye/analysis/viewer/layers_widget.py +415 -0
  60. microEye/analysis/viewer/localizations.py +1304 -0
  61. microEye/analysis/viewer/psf.py +1003 -0
  62. microEye/analysis/viewer/volume.py +456 -0
  63. microEye/hardware/__init__.py +3 -0
  64. microEye/hardware/cams/__init__.py +29 -0
  65. microEye/hardware/cams/camera_calibration.py +99 -0
  66. microEye/hardware/cams/camera_list.py +528 -0
  67. microEye/hardware/cams/camera_options.py +694 -0
  68. microEye/hardware/cams/camera_panel.py +941 -0
  69. microEye/hardware/cams/dummy/__init__.py +1 -0
  70. microEye/hardware/cams/dummy/dummy_panel.py +759 -0
  71. microEye/hardware/cams/jobs.py +497 -0
  72. microEye/hardware/cams/line_profiler.py +99 -0
  73. microEye/hardware/cams/linescan/IR_Cam.py +474 -0
  74. microEye/hardware/cams/linescan/__init__.py +1 -0
  75. microEye/hardware/cams/micam.py +524 -0
  76. microEye/hardware/cams/pco/__init__.py +58 -0
  77. microEye/hardware/cams/pco/enums.py +382 -0
  78. microEye/hardware/cams/pco/pco_cam.py +761 -0
  79. microEye/hardware/cams/pco/pco_panel.py +477 -0
  80. microEye/hardware/cams/shortcuts.py +312 -0
  81. microEye/hardware/cams/thorlabs/__init__.py +1 -0
  82. microEye/hardware/cams/thorlabs/thorlabs.py +1508 -0
  83. microEye/hardware/cams/thorlabs/thorlabs_panel.py +850 -0
  84. microEye/hardware/cams/ueye/__init__.py +1 -0
  85. microEye/hardware/cams/ueye/ueye_camera.py +1023 -0
  86. microEye/hardware/cams/ueye/ueye_panel.py +861 -0
  87. microEye/hardware/cams/vimba/__init__.py +1 -0
  88. microEye/hardware/cams/vimba/vimba_cam.py +1000 -0
  89. microEye/hardware/cams/vimba/vimba_panel.py +813 -0
  90. microEye/hardware/device.py +60 -0
  91. microEye/hardware/lasers/__init__.py +13 -0
  92. microEye/hardware/lasers/io_matchbox.py +791 -0
  93. microEye/hardware/lasers/io_params.py +85 -0
  94. microEye/hardware/lasers/io_single_laser.py +742 -0
  95. microEye/hardware/lasers/laser_relay.py +594 -0
  96. microEye/hardware/mieye/__init__.py +1 -0
  97. microEye/hardware/mieye/acquisition_manager.py +467 -0
  98. microEye/hardware/mieye/devices_manager.py +533 -0
  99. microEye/hardware/mieye/miEye.py +659 -0
  100. microEye/hardware/misc/__init__.py +0 -0
  101. microEye/hardware/misc/acquisition_view.py +71 -0
  102. microEye/hardware/misc/reglo.py +761 -0
  103. microEye/hardware/misc/temp.py +188 -0
  104. microEye/hardware/port_config.py +59 -0
  105. microEye/hardware/protocols/__init__.py +2 -0
  106. microEye/hardware/protocols/actions.py +402 -0
  107. microEye/hardware/protocols/actions_items.py +703 -0
  108. microEye/hardware/protocols/designer.py +244 -0
  109. microEye/hardware/protocols/scene_manager.py +191 -0
  110. microEye/hardware/protocols/serialization.py +97 -0
  111. microEye/hardware/pycromanager/__init__.py +16 -0
  112. microEye/hardware/pycromanager/core.py +1433 -0
  113. microEye/hardware/pycromanager/devices.py +461 -0
  114. microEye/hardware/pycromanager/enums.py +107 -0
  115. microEye/hardware/pycromanager/headless.py +153 -0
  116. microEye/hardware/pycromanager/utils.py +34 -0
  117. microEye/hardware/pycromanager/widgets/__init__.py +5 -0
  118. microEye/hardware/pycromanager/widgets/bridges.py +407 -0
  119. microEye/hardware/pycromanager/widgets/headless_manager.py +258 -0
  120. microEye/hardware/pycromanager/widgets/headless_options.py +224 -0
  121. microEye/hardware/pycromanager/widgets/pycro_panel.py +455 -0
  122. microEye/hardware/stages/__init__.py +18 -0
  123. microEye/hardware/stages/elliptec/__init__.py +5 -0
  124. microEye/hardware/stages/elliptec/baseDevice.py +314 -0
  125. microEye/hardware/stages/elliptec/device.py +384 -0
  126. microEye/hardware/stages/elliptec/deviceID.py +212 -0
  127. microEye/hardware/stages/elliptec/devicePort.py +379 -0
  128. microEye/hardware/stages/elliptec/deviceStatus.py +65 -0
  129. microEye/hardware/stages/elliptec/devicesView.py +706 -0
  130. microEye/hardware/stages/elliptec/ellDevices.py +134 -0
  131. microEye/hardware/stages/elliptec/messageUpdater.py +34 -0
  132. microEye/hardware/stages/elliptec/motorInfo.py +153 -0
  133. microEye/hardware/stages/elliptec/stage.py +62 -0
  134. microEye/hardware/stages/elliptec/test.py +139 -0
  135. microEye/hardware/stages/kinesis/__init__.py +1 -0
  136. microEye/hardware/stages/kinesis/kdc101/__init__.py +1 -0
  137. microEye/hardware/stages/kinesis/kdc101/enums.py +1002 -0
  138. microEye/hardware/stages/kinesis/kdc101/factory.py +171 -0
  139. microEye/hardware/stages/kinesis/kdc101/kdc101.py +718 -0
  140. microEye/hardware/stages/kinesis/kinesis.py +776 -0
  141. microEye/hardware/stages/piezo_concept.py +607 -0
  142. microEye/hardware/stages/stabilizer.py +785 -0
  143. microEye/hardware/stages/stage.py +89 -0
  144. microEye/hardware/widgets/__init__.py +10 -0
  145. microEye/hardware/widgets/controller.py +246 -0
  146. microEye/hardware/widgets/devices.py +133 -0
  147. microEye/hardware/widgets/focusWidget.py +264 -0
  148. microEye/hardware/widgets/qlist_slider.py +113 -0
  149. microEye/hardware/widgets/scan_acquisition.py +424 -0
  150. microEye/icons/1024.png +0 -0
  151. microEye/icons/128.png +0 -0
  152. microEye/icons/16.png +0 -0
  153. microEye/icons/24.png +0 -0
  154. microEye/icons/256.png +0 -0
  155. microEye/icons/32.png +0 -0
  156. microEye/icons/48.png +0 -0
  157. microEye/icons/512.png +0 -0
  158. microEye/icons/64.png +0 -0
  159. microEye/icons/__init__.py +0 -0
  160. microEye/icons/close.svg +88 -0
  161. microEye/icons/mieye.png +0 -0
  162. microEye/icons/min.svg +83 -0
  163. microEye/icons/viewer.png +0 -0
  164. microEye/launcher.py +42 -0
  165. microEye/qt.py +181 -0
  166. microEye/utils/__init__.py +2 -0
  167. microEye/utils/enum_encoder.py +10 -0
  168. microEye/utils/expandable_groupbox.py +93 -0
  169. microEye/utils/gui_helper.py +457 -0
  170. microEye/utils/hid/__init__.py +8 -0
  171. microEye/utils/hid/controller.py +153 -0
  172. microEye/utils/hid/device.py +63 -0
  173. microEye/utils/hid/enums.py +140 -0
  174. microEye/utils/hid/utils.py +58 -0
  175. microEye/utils/labelled_slider.py +134 -0
  176. microEye/utils/metadata.py +599 -0
  177. microEye/utils/metadata_tree.py +718 -0
  178. microEye/utils/micro_launcher.py +245 -0
  179. microEye/utils/parameter_tree.py +325 -0
  180. microEye/utils/pyscripting.py +444 -0
  181. microEye/utils/retry_exec.py +35 -0
  182. microEye/utils/start_gui.py +112 -0
  183. microEye/utils/thread_worker.py +115 -0
  184. microEye/utils/uImage.py +1512 -0
  185. microeye-2.3.2.dist-info/METADATA +401 -0
  186. microeye-2.3.2.dist-info/RECORD +190 -0
  187. microeye-2.3.2.dist-info/WHEEL +5 -0
  188. microeye-2.3.2.dist-info/entry_points.txt +2 -0
  189. microeye-2.3.2.dist-info/licenses/LICENSE +674 -0
  190. microeye-2.3.2.dist-info/top_level.txt +1 -0
@@ -0,0 +1,657 @@
1
+ import math
2
+
3
+ import numba as nb
4
+ import numpy as np
5
+
6
+ from microEye.analysis.fitting.pyfit3Dcspline.constants import *
7
+
8
+
9
+ @nb.njit(nb.float32(nb.int32, nb.float32, nb.float32), cache=True)
10
+ def kernel_IntGauss1D(ii, x, sigma):
11
+ '''
12
+ `kernel_IntGauss1D` computes the cumulative probability of a Gaussian distribution
13
+ between two points determined by `ii` and `x`, adjusted for the width of the
14
+ distribution specified by `sigma`.
15
+
16
+ Parameters
17
+ ----------
18
+ ii : int
19
+ The index of the point to compute the cumulative probability for
20
+ x : float
21
+ The center of the Gaussian distribution
22
+ sigma : float
23
+ The width of the Gaussian distribution
24
+ '''
25
+ norm = 1.0 / (2.0 * sigma * sigma)
26
+
27
+ return 0.5 * (
28
+ math.erf((ii - x + 0.5) * math.sqrt(norm))
29
+ - math.erf((ii - x - 0.5) * math.sqrt(norm))
30
+ )
31
+
32
+
33
+ @nb.njit(nb.float32(nb.float32, nb.float32, nb.float32, nb.float32), cache=True)
34
+ def kernel_alpha(z, Ax, Bx, d):
35
+ '''compute coefficient for alpha
36
+
37
+ Parameters
38
+ ----------
39
+ z : float
40
+ ???
41
+ Ax : float
42
+ ???
43
+ Bx : float
44
+ ???
45
+ d : float
46
+ ???
47
+
48
+ Returns
49
+ -------
50
+ float
51
+ alpha value
52
+ '''
53
+
54
+ return 1.0 + math.pow(z / d, 2) + Ax * math.pow(z / d, 3) + Bx * math.pow(z / d, 4)
55
+
56
+
57
+ @nb.njit(nb.float32(nb.float32, nb.float32, nb.float32, nb.float32), cache=True)
58
+ def kernel_dalphadz(z, Ax, Bx, d) -> float:
59
+ '''compute first derivative for alpha in relation to z
60
+
61
+ Parameters
62
+ ----------
63
+ z : float
64
+ ???
65
+ Ax : float
66
+ ???
67
+ Bx : float
68
+ ???
69
+ d : float
70
+ ???
71
+
72
+ Returns
73
+ -------
74
+ float
75
+ first derivative for alpha value
76
+ '''
77
+
78
+ return (
79
+ 2.0 * z / (d * d)
80
+ + 3.0 * Ax * math.pow(z, 2) / (d * d * d)
81
+ + 4.0 * Bx * math.pow(z, 3) / math.pow(d, 4)
82
+ )
83
+
84
+
85
+ @nb.njit(nb.float32(nb.float32, nb.float32, nb.float32, nb.float32), cache=True)
86
+ def kernel_d2alphadz2(z, Ax, Bx, d):
87
+ '''compute second derivative for alpha in relation to z
88
+
89
+ Parameters
90
+ ----------
91
+ z : float
92
+ ???
93
+ Ax : float
94
+ ???
95
+ Bx : float
96
+ ???
97
+ d : float
98
+ ???
99
+
100
+ Returns
101
+ -------
102
+ float
103
+ second derivative for alpha value
104
+ '''
105
+
106
+ return (
107
+ 2.0 / (d * d)
108
+ + 6.0 * Ax * z / (d * d * d)
109
+ + 12.0 * Bx * math.pow(z, 2) / math.pow(d, 4)
110
+ )
111
+
112
+
113
+ @nb.njit(
114
+ nb.types.Tuple((nb.float32, nb.float32))(
115
+ nb.int32, nb.float32, nb.float32, nb.float32, nb.float32, nb.boolean
116
+ ),
117
+ cache=True,
118
+ )
119
+ def kernel_DerivativeIntGauss1D(ii, x, sigma, N, PSFy, calc_d2):
120
+ '''compute the derivative of the 1D gaussian
121
+
122
+ Parameters
123
+ ----------
124
+ ii : int
125
+ ???
126
+ x : float
127
+ ???
128
+ sigma : float
129
+ ???
130
+ N : float
131
+ ???
132
+ PSFy : float
133
+ ???
134
+ calc_d2 : bool
135
+ calculate d2udt2
136
+
137
+ Returns
138
+ -------
139
+ (float, float)
140
+ dudt, d2udt2 values
141
+ '''
142
+ a = math.exp(-0.5 * math.pow(((ii + 0.5 - x) / sigma), 2))
143
+ b = math.exp(-0.5 * math.pow((ii - 0.5 - x) / sigma, 2))
144
+
145
+ dudt = -(N / (math.sqrt(2.0 * pi) * sigma)) * (a - b) * PSFy
146
+ d2udt2 = 0
147
+
148
+ if calc_d2:
149
+ d2udt2 = (
150
+ -(N / (math.sqrt(2.0 * pi) * math.pow(sigma, 3)))
151
+ * ((ii + 0.5 - x) * a - (ii - 0.5 - x) * b)
152
+ * PSFy
153
+ )
154
+
155
+ return dudt, d2udt2
156
+
157
+
158
+ @nb.njit(
159
+ nb.types.Tuple((nb.float32, nb.float32))(
160
+ nb.int32, nb.float32, nb.float32, nb.float32, nb.float32, nb.boolean
161
+ ),
162
+ cache=True,
163
+ )
164
+ def kernel_DerivativeIntGauss1DSigma(ii, x, Sx, N, PSFy, calc_d2):
165
+ '''compute the derivative of the 1D gaussian
166
+
167
+ Parameters
168
+ ----------
169
+ ii : int
170
+ ???
171
+ x : float
172
+ ???
173
+ sigma : float
174
+ ???
175
+ N : float
176
+ ???
177
+ PSFy : float
178
+ ???
179
+ calc_d2 : bool
180
+ calculate d2udt2
181
+
182
+ Returns
183
+ -------
184
+ (float, float)
185
+ dudt, d2udt2 values
186
+ '''
187
+ ax = math.exp(-0.5 * math.pow(((ii + 0.5 - x) / Sx), 2))
188
+ bx = math.exp(-0.5 * math.pow((ii - 0.5 - x) / Sx, 2))
189
+
190
+ dudt = (
191
+ -(N / (math.sqrt(2 * pi) * Sx * Sx))
192
+ * (ax * (ii - x + 0.5) - bx * (ii - x - 0.5))
193
+ * PSFy
194
+ )
195
+ d2udt2 = 0
196
+
197
+ if calc_d2:
198
+ d2udt2 = (
199
+ -(2 / Sx) * dudt
200
+ - (N / (math.sqrt(2 * pi) * math.pow(Sx, 5)))
201
+ * (ax * math.pow((ii - x + 0.5), 3) - bx * math.pow((ii - x - 0.5), 3))
202
+ * PSFy
203
+ )
204
+
205
+ return dudt, d2udt2
206
+
207
+
208
+ @nb.njit(
209
+ nb.types.Tuple((nb.float32, nb.float32))(
210
+ nb.int32,
211
+ nb.int32,
212
+ nb.float32,
213
+ nb.float32,
214
+ nb.float32,
215
+ nb.float32,
216
+ nb.float32,
217
+ nb.float32,
218
+ nb.boolean,
219
+ ),
220
+ cache=True,
221
+ )
222
+ def kernel_DerivativeIntGauss2DSigma(ii, jj, x, y, S, N, PSFx, PSFy, calc_d2):
223
+ '''compute the derivative of the 2D gaussian
224
+
225
+ Parameters
226
+ ----------
227
+ ii : int
228
+ ???
229
+ jj : int
230
+ ???
231
+ x : float
232
+ ???
233
+ y : float
234
+ ???
235
+ S : float
236
+ ???
237
+ N : float
238
+ ???
239
+ PSFx : float
240
+ ???
241
+ PSFy : float
242
+ ???
243
+ calc_d2 : bool
244
+ calculate d2udt2
245
+
246
+ Returns
247
+ -------
248
+ (float, float)
249
+ dudt, d2udt2 values
250
+ '''
251
+
252
+ dSx, ddSx = kernel_DerivativeIntGauss1DSigma(ii, x, S, N, PSFy, calc_d2)
253
+ dSy, ddSy = kernel_DerivativeIntGauss1DSigma(jj, y, S, N, PSFx, calc_d2)
254
+
255
+ dudt = dSx + dSy
256
+ d2udt2 = 0
257
+ if calc_d2:
258
+ d2udt2 = ddSx + ddSy
259
+
260
+ return dudt, d2udt2
261
+
262
+
263
+ @nb.njit(nb.types.Tuple((nb.float32, nb.float32))(nb.int64, nb.float32[:]), cache=True)
264
+ def kernel_CenterofMass2D(sz, data):
265
+ '''compute the 2D center of mass of a subregion
266
+
267
+ Parameters
268
+ ----------
269
+ sz : _type_
270
+ nxn size of the subregion
271
+ data : _type_
272
+ subregion to search
273
+
274
+ Returns
275
+ -------
276
+ tuple[float, float]
277
+ (x, y) coordinate to return
278
+ '''
279
+ x_sum = y_sum = total_intensity = 0.0
280
+ for ii in range(sz):
281
+ for jj in range(sz):
282
+ intensity = data[sz * jj + ii]
283
+ x_sum += intensity * ii
284
+ y_sum += intensity * jj
285
+ total_intensity += intensity
286
+
287
+ if total_intensity > 0:
288
+ x = x_sum / total_intensity
289
+ y = y_sum / total_intensity
290
+ else:
291
+ x = y = sz / 2 # Default to center if total intensity is zero
292
+
293
+ return x, y
294
+
295
+
296
+ @nb.njit(
297
+ nb.types.Tuple((nb.float32, nb.float32))(nb.int32, nb.float32, nb.float32[:]),
298
+ cache=True,
299
+ )
300
+ def kernel_GaussFMaxMin2D(sz, sigma, data):
301
+ '''returns filtered min and pixels of a given subregion
302
+
303
+ Parameters
304
+ ----------
305
+ sz : int
306
+ nxn size of the subregion
307
+ sigma : float
308
+ used in filter calculation
309
+ data : float[]
310
+ the subregion to search
311
+
312
+ Returns
313
+ -------
314
+ tuple[float, float]
315
+ (MaxN, MinBG) maximum pixel value, minimum background value.
316
+ '''
317
+ # int ii, jj, kk, ll;
318
+ MaxN = 0.0
319
+ MinBG = 10e10 # big
320
+
321
+ norm = 1.0 / (2.0 * sigma * sigma)
322
+ # loop over all pixels
323
+ for kk in range(sz):
324
+ for ll in range(sz):
325
+ MaxN = max(MaxN, data[kk * sz + ll])
326
+ MinBG = min(MinBG, data[kk * sz + ll])
327
+
328
+ return MaxN, MinBG
329
+
330
+
331
+ @nb.njit(
332
+ nb.types.Tuple((nb.float32[:], nb.float32))(
333
+ nb.int32, nb.int32, nb.float32, nb.float32[:], nb.float32[:]
334
+ ),
335
+ cache=True,
336
+ )
337
+ def kernel_DerivativeGauss2D(ii, jj, PSFSigma, theta, dudt):
338
+ '''compute DerivativeGauss2D
339
+
340
+ Parameters
341
+ ----------
342
+ ii : int
343
+ _description_
344
+ jj : int
345
+ _description_
346
+ PSFSigma : float
347
+ _description_
348
+ theta : float[]
349
+ _description_
350
+ dudt : float[]
351
+ _description_
352
+
353
+ Returns
354
+ -------
355
+ tuple[ndarray, float]
356
+ (dudt, model)
357
+ '''
358
+ PSFx = kernel_IntGauss1D(ii, theta[0], PSFSigma)
359
+ PSFy = kernel_IntGauss1D(jj, theta[1], PSFSigma)
360
+
361
+ model = theta[3] + theta[2] * PSFx * PSFy
362
+
363
+ # calculating derivatives
364
+ dudt[0], _ = kernel_DerivativeIntGauss1D(
365
+ ii, theta[0], PSFSigma, theta[2], PSFy, False
366
+ )
367
+ dudt[1], _ = kernel_DerivativeIntGauss1D(
368
+ jj, theta[1], PSFSigma, theta[2], PSFx, False
369
+ )
370
+ dudt[2] = PSFx * PSFy
371
+ dudt[3] = 1.0
372
+
373
+ return dudt, model
374
+
375
+
376
+ @nb.njit(
377
+ nb.types.Tuple((nb.float32[:], nb.float32))(
378
+ nb.int32, nb.int32, nb.float32[:], nb.float32[:]
379
+ ),
380
+ cache=True,
381
+ )
382
+ def kernel_DerivativeGauss2D_sigma(ii, jj, theta, dudt):
383
+ '''compute DerivativeGauss2D_sigma
384
+
385
+ Parameters
386
+ ----------
387
+ ii : int
388
+ _description_
389
+ jj : int
390
+ _description_
391
+ PSFSigma : float
392
+ _description_
393
+ theta : float[]
394
+ _description_
395
+ dudt : float[]
396
+ _description_
397
+
398
+ Returns
399
+ -------
400
+ tuple[ndarray, float]
401
+ (dudt, model)
402
+ '''
403
+ PSFx = kernel_IntGauss1D(ii, theta[0], theta[4])
404
+ PSFy = kernel_IntGauss1D(jj, theta[1], theta[4])
405
+
406
+ model = theta[3] + theta[2] * PSFx * PSFy
407
+
408
+ dudt[0], _ = kernel_DerivativeIntGauss1D(
409
+ ii, theta[0], theta[4], theta[2], PSFy, False
410
+ )
411
+ dudt[1], _ = kernel_DerivativeIntGauss1D(
412
+ jj, theta[1], theta[4], theta[2], PSFx, False
413
+ )
414
+ dudt[4], _ = kernel_DerivativeIntGauss2DSigma(
415
+ ii, jj, theta[0], theta[1], theta[4], theta[2], PSFx, PSFy, False
416
+ )
417
+ dudt[2] = PSFx * PSFy
418
+ dudt[3] = 1.0
419
+
420
+ return dudt, model
421
+
422
+
423
+ @nb.njit(cache=True)
424
+ def kernel_DerivativeIntGauss2Dz(
425
+ ii,
426
+ jj,
427
+ theta,
428
+ PSFSigma_x,
429
+ PSFSigma_y,
430
+ Ax,
431
+ Ay,
432
+ Bx,
433
+ By,
434
+ gamma,
435
+ d,
436
+ dudt,
437
+ d2udt2,
438
+ calc_d2,
439
+ ):
440
+ '''compute the derivative of the 2D gaussian
441
+
442
+ Parameters
443
+ ----------
444
+ ii : int
445
+ _description_
446
+ jj : int
447
+ _description_
448
+ theta : float
449
+ _description_
450
+ PSFSigma_x : float
451
+ _description_
452
+ PSFSigma_y : float
453
+ _description_
454
+ Ax : float
455
+ _description_
456
+ Ay : float
457
+ _description_
458
+ Bx : float
459
+ _description_
460
+ By : float
461
+ _description_
462
+ gamma : float
463
+ _description_
464
+ d : float
465
+ _description_
466
+ pPSFx : float
467
+ _description_
468
+ pPSFy : float
469
+ _description_
470
+ dudt : float
471
+ _description_
472
+ d2udt2 : float
473
+ _description_
474
+ calc_d2 : bool
475
+ calculate d2udt2
476
+
477
+ Returns
478
+ -------
479
+ tuple[...]
480
+ (PSFx, PSFy, dudt, d2udt2, model)
481
+ '''
482
+
483
+ z = theta[4]
484
+
485
+ alphax = kernel_alpha(z - gamma, Ax, Bx, d)
486
+ alphay = kernel_alpha(z + gamma, Ay, By, d)
487
+
488
+ Sx = PSFSigma_x * math.sqrt(alphax)
489
+ Sy = PSFSigma_y * math.sqrt(alphay)
490
+
491
+ PSFx = kernel_IntGauss1D(ii, theta[0], Sx)
492
+ PSFy = kernel_IntGauss1D(jj, theta[1], Sy)
493
+ # pPSFx = PSFx
494
+ # pPSFy = PSFy
495
+
496
+ dudt[0], ddx = kernel_DerivativeIntGauss1D(ii, theta[0], Sx, theta[2], PSFy, True)
497
+ dudt[1], ddy = kernel_DerivativeIntGauss1D(jj, theta[1], Sy, theta[2], PSFx, True)
498
+ dSx, ddSx = kernel_DerivativeIntGauss1DSigma(ii, theta[0], Sx, theta[2], PSFy, True)
499
+ dSy, ddSy = kernel_DerivativeIntGauss1DSigma(jj, theta[1], Sy, theta[2], PSFx, True)
500
+
501
+ dSdalpha_x = PSFSigma_x / (2.0 * math.sqrt(alphax))
502
+ dSdalpha_y = PSFSigma_y / (2.0 * math.sqrt(alphay))
503
+
504
+ dSdzx = dSdalpha_x * kernel_dalphadz(z - gamma, Ax, Bx, d)
505
+ dSdzy = dSdalpha_y * kernel_dalphadz(z + gamma, Ay, By, d)
506
+ dudt[4] = dSx * dSdzx + dSy * dSdzy
507
+
508
+ dudt[2] = PSFx * PSFy
509
+ dudt[3] = 1.0
510
+
511
+ model = theta[3] + theta[2] * PSFx * PSFy
512
+
513
+ if calc_d2:
514
+ d2udt2[0] = ddx
515
+ d2udt2[1] = ddy
516
+
517
+ d2Sdalpha2_x = -PSFSigma_x / (4.0 * math.pow(alphax, 1.5))
518
+ d2Sdalpha2_y = -PSFSigma_y / (4.0 * math.pow(alphay, 1.5))
519
+
520
+ ddSddzx = d2Sdalpha2_x * math.pow(
521
+ kernel_dalphadz(z - gamma, Ax, Bx, d), 2
522
+ ) + dSdalpha_x * kernel_d2alphadz2(z - gamma, Ax, Bx, d)
523
+ ddSddzy = d2Sdalpha2_y * math.pow(
524
+ kernel_dalphadz(z + gamma, Ay, By, d), 2
525
+ ) + dSdalpha_y * kernel_d2alphadz2(z + gamma, Ay, By, d)
526
+
527
+ d2udt2[4] = (
528
+ ddSx * (dSdzx * dSdzx)
529
+ + dSx * ddSddzx
530
+ + ddSy * (dSdzy * dSdzy)
531
+ + dSy * ddSddzy
532
+ )
533
+ d2udt2[2] = 0.0
534
+ d2udt2[3] = 0.0
535
+
536
+ return PSFx, PSFy, dudt, d2udt2, model
537
+
538
+
539
+ @nb.njit(
540
+ nb.types.Tuple((nb.float32[:], nb.float32))(
541
+ nb.int32, nb.int32, nb.float32[:], nb.float32[:]
542
+ ),
543
+ cache=True,
544
+ )
545
+ def kernel_DerivativeGauss2D_sigmaxy(ii, jj, theta, dudt):
546
+ '''
547
+ Parameters
548
+ ----------
549
+ ii : int
550
+ The index for the x coordinate
551
+ jj : int
552
+ The index for the y coordinate
553
+ theta : float[]
554
+ Parameters for the Gaussian function
555
+ dudt : float[]
556
+ Output array to store derivatives
557
+
558
+ Returns
559
+ -------
560
+ tuple[ndarray, float]
561
+ (dudt, model)
562
+ '''
563
+ # Compute PSFx and PSFy using kernel_IntGauss1D
564
+ PSFx = kernel_IntGauss1D(ii, theta[0], theta[4])
565
+ PSFy = kernel_IntGauss1D(jj, theta[1], theta[5])
566
+
567
+ # Compute derivatives with respect to x and y
568
+ dudt[0], _ = kernel_DerivativeIntGauss1D(
569
+ ii, theta[0], theta[4], theta[2], PSFy, False
570
+ )
571
+ dudt[1], _ = kernel_DerivativeIntGauss1D(
572
+ jj, theta[1], theta[5], theta[2], PSFx, False
573
+ )
574
+ # Compute derivatives with respect to sigma
575
+ dudt[4], _ = kernel_DerivativeIntGauss1DSigma(
576
+ ii, theta[0], theta[4], theta[2], PSFy, False
577
+ )
578
+ dudt[5], _ = kernel_DerivativeIntGauss1DSigma(
579
+ jj, theta[1], theta[5], theta[2], PSFx, False
580
+ )
581
+ # Update the output derivatives
582
+ dudt[2] = PSFx * PSFy
583
+ dudt[3] = 1.0
584
+
585
+ # Update the model output
586
+ model = theta[3] + theta[2] * PSFx * PSFy
587
+
588
+ return dudt, model
589
+
590
+
591
+ @nb.njit(cache=True)
592
+ def kernel_MatInvN(M, Minv, DiagMinv, sz):
593
+ '''nxn partial matrix inversion
594
+
595
+ Parameters
596
+ ----------
597
+ M : _type_
598
+ matrix to inverted
599
+ Minv : _type_
600
+ Minv inverted matrix result
601
+ DiagMinv : _type_
602
+ DiagMinv just the inverted diagonal
603
+ sz : _type_
604
+ sz size of the matrix
605
+ '''
606
+ tmp1 = 0.0
607
+ yy = np.zeros(sz, np.float32)
608
+
609
+ for jj in range(sz):
610
+ # calculate upper matrix
611
+ for ii in range(jj + 1):
612
+ # deal with ii-1 in the sum, set sum(kk=0->ii-1) when ii=0 to zero
613
+ if ii > 0:
614
+ for kk in range(ii):
615
+ tmp1 += M[ii + kk * sz] * M[kk + jj * sz]
616
+ M[ii + jj * sz] -= tmp1
617
+ tmp1 = 0
618
+
619
+ for ii in range(jj + 1, sz, 1):
620
+ if jj > 0:
621
+ for kk in range(jj):
622
+ tmp1 += M[ii + kk * sz] * M[kk + jj * sz]
623
+ M[ii + jj * sz] = (1 / M[jj + jj * sz]) * (M[ii + jj * sz] - tmp1)
624
+ tmp1 = 0
625
+ else:
626
+ M[ii + jj * sz] = (1 / M[jj + jj * sz]) * M[ii + jj * sz]
627
+
628
+ tmp1 = 0
629
+
630
+ for num in range(sz):
631
+ # calculate yy
632
+ if num == 0:
633
+ yy[0] = 1
634
+ else:
635
+ yy[0] = 0
636
+
637
+ for ii in range(1, sz, 1):
638
+ b = 1 if ii == num else 0
639
+ for jj in range(ii):
640
+ tmp1 += M[ii + jj * sz] * yy[jj]
641
+ yy[ii] = b - tmp1
642
+ tmp1 = 0
643
+
644
+ # calculate Minv
645
+ Minv[sz - 1 + num * sz] = yy[sz - 1] / M[(sz - 1) + (sz - 1) * sz]
646
+
647
+ for ii in range(sz - 2, -1, -1):
648
+ for jj in range(ii + 1, sz, 1):
649
+ tmp1 += M[ii + jj * sz] * Minv[jj + num * sz]
650
+ Minv[ii + num * sz] = (1 / M[ii + ii * sz]) * (yy[ii] - tmp1)
651
+ tmp1 = 0
652
+
653
+ # if DiagMinv:
654
+ for ii in range(sz):
655
+ DiagMinv[ii] = Minv[ii * sz + ii]
656
+
657
+ return Minv, DiagMinv