Merge pull request #36 from PAMGuard/main

Merging from PM Main
This commit is contained in:
Douglas Gillespie 2023-01-25 16:32:11 +00:00 committed by GitHub
commit 738c9ab6dc
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
59 changed files with 2034 additions and 908 deletions

View File

@ -386,9 +386,12 @@ PamguardBeta_ViewerMode.exe):</p>
<p class=MsoNormal><em><span style='font-family:"Calibri",sans-serif'>&nbsp;</span></em></p>
<h1><a name="_LATEST_VERSION_2.02.03"></a><em><span style='font-size:12.0pt;
font-family:"Cambria",serif;font-style:normal'><a
href="#_Latest_Version_2.02.06">LATEST VERSION 2.02.06 November 2022</a></span></em></h1>
<h1><a name="_LATEST_VERSION_2.02.03"></a><a name="_VERSION_2.02.07_January"></a><em><span
style='font-size:12.0pt;font-family:"Cambria",serif;font-style:normal'><a
href="#_Latest_Version_2.02.07">LATEST VERSION 2.02.07 January 2023</a></span></em></h1>
<h1><em><span style='font-size:12.0pt;font-family:"Cambria",serif;font-style:
normal'><a href="#_Latest_Version_2.02.06">Version 2.02.06 November 2022</a></span></em></h1>
<h1><em><span style='font-size:12.0pt;font-family:"Cambria",serif;font-style:
normal'><a href="#_Latest_Version_2.02.05">Version 2.02.05 October 2022</a></span></em></h1>
@ -447,8 +450,47 @@ Version 2.00.10 June 2017</a></span></h1>
<h1><span style='font-size:12.0pt'><a href="#_Older_Versions">Older Versions</a></span></h1>
<h1><a name="_Latest_Version_2.02.03_1"></a><a name="_Latest_Version_2.02.05"></a><a
name="_Latest_Version_2.02.06"></a><span lang=EN-US>Latest Version 2.02.06
November 2022</span></h1>
name="_Latest_Version_2.02.06"></a><a name="_Latest_Version_2.02.07"></a><span
lang=EN-US>Latest Version 2.02.07 January 2023</span></h1>
<h2><span lang=EN-US>Bug Fixes</span></h2>
<p class=MsoNormal><span lang=EN-US>Use of localization sensor and orientation data
for static hydrophones had a bug whereby it would continually forget angle
offsets applied to static hydrophones in viewer mode. This is now fixed. </span></p>
<p class=MsoNormal><span lang=EN-US>Click tool bar: Correctly shows event
selection options even if no species classification options are in place. </span></p>
<p class=MsoNormal><span lang=EN-US>Fixed Landmarks: Earlier versions were
losing these every time PAMGuard started or new data were loaded in viewer
mode. Now fixed. </span></p>
<p class=MsoNormal><span lang=EN-US>ROCCA: Fixed (another) memory leak which
caused PAMGuard to crash when processing large data sets with the ROCCA
classifier. </span></p>
<p class=MsoNormal><span lang=EN-US>Ishmael Modules: Fixed bug which
occasionally caused crashes when processing many files offline. </span></p>
<p class=MsoNormal><span lang=EN-US>PAMDog: Fixed bug in watchdog program which
was trying to start PAMGuard before modules were fully loaded. The watchdog now
correctly waits until modules are loaded before attempting to start PAMGuard
processing.</span></p>
<h2><span lang=EN-US>New Features</span></h2>
<p class=MsoNormal><span lang=EN-US>New sound type for simulated sounds which
generates random chirps between around 200 and 800Hz, roughly the frequency
youd expect sound from higher frequency baleen whales, such as humpbacks, to
vocalise at. &nbsp;&nbsp;</span></p>
<p class=MsoNormal><span lang=EN-US>Hiding tool tips. A menu item to
permanently turn off all tool tips, or tap the Esc key to turn them off for 6
seconds if they are getting in the way, particularly when trying to interact
with displays using the mouse. </span></p>
<h1><span lang=EN-US>Version 2.02.06 November 2022</span></h1>
<h2><span lang=EN-US>Bug Fixes</span></h2>
@ -488,10 +530,10 @@ system to have nested classifiers which can be enabled or disabled. </span></p>
<p class=MsoNormal><span lang=EN-US>Changes to classification GUI to
accommodate the new classification system.</span></p>
<p class=MsoNormal><span lang=EN-US>Addition of data selectors to the minimum number
of clicks accepted by the classifier. This allows the click-by-click classifier
and the click train detector to be used to together to improve classification
accuracy. </span></p>
<p class=MsoNormal><span lang=EN-US>Addition of data selectors to the minimum
number of clicks accepted by the classifier. This allows the click-by-click
classifier and the click train detector to be used to together to improve
classification accuracy. </span></p>
<p class=MsoNormal><b><span lang=EN-US>Bug fixes</span></b></p>
@ -710,8 +752,9 @@ lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nb
lang=EN-US> </span>Extended XML-output support to all of the modules </p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>8. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
Updates to the simulated sounds in the Sound Acquisition module </p>
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span
lang=EN-US> </span>Updates to the simulated sounds in the Sound Acquisition
module </p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>9. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span
@ -749,9 +792,9 @@ decimating/upsampling by a non-integer amount </p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>16. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
Noise Level Outputs - as an aid to performance diagnosis, some detectors
(currently the GPL, Click Detector and Whistle and Moan Detector) are
outputting additional noise metrics to their binary output files. These can be
read with the <a href="https://sourceforge.net/projects/pamguard/files/Matlab/">PAMGuard
(currently the GPL, Click Detector and Whistle and Moan Detector) are outputting
additional noise metrics to their binary output files. These can be read with
the <a href="https://sourceforge.net/projects/pamguard/files/Matlab/">PAMGuard
Matlab library</a> and used to diagnose system performance in varying noise
conditions. Improved displays within PAMGuard for these noise metrics will be
included in a future release. </p>
@ -759,10 +802,10 @@ included in a future release. </p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>17. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
An implementation of the Generalized Power Law Detector, developed by Tyler
Helble ([Helble et al., ‘A generalized power-law detection algorithm for
humpback whale vocalizations’, The Journal of the Acoustical Society of
America, vol. 131, no. 4, pp. 2682–2699, 2012) is now available. For
details, see the online help </p>
Helble ([Helble et al., ÃÂA generalized power-law detection algorithm for humpback
whale vocalizationsÃÂ, The Journal of the Acoustical Society of America, vol.
131, no. 4, pp. 2682ÃÂ2699, 2012) is now available. For details, see the
online help </p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>18. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
@ -1021,17 +1064,18 @@ lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nb
Add 3D map for target motion module. </p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>6. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
Add option to alarm module to attach screenshots of all frames to email alerts.
</p>
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span
lang=EN-US> </span>Add option to alarm module to attach screenshots of all
frames to email alerts. </p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>7. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
Add Beamformer and Bearing Localiser modules </p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>8. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
Added Global Medium Manager, to switch between air and water mediums </p>
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span
lang=EN-US> </span>Added Global Medium Manager, to switch between air and water
mediums </p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>9. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
@ -1055,9 +1099,10 @@ lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nb
lang=EN-US> </span>Added ctrl-p hotkey to print-screen button. </p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>14. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
Update simulated daq so that it generates new random noise correctly on each
call rather then recycling old data. Makes the output more spectrally flat. </p>
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span
lang=EN-US> </span>Update simulated daq so that it generates new random noise
correctly on each call rather then recycling old data. Makes the output more
spectrally flat. </p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>14. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
@ -1069,10 +1114,11 @@ placement, etc.</p>
<h1><a name="_Latest_Beta_Version_2.01.03"></a><span lang=EN-US>Version 2.01.03
February 2020</span></h1>
<p class=MsoNormal><b>If you are upgrading from a PAMGuard core release (1.15.xx),
PAMGuard Version 2 contains major updates. You should read and understand the
notes listed for <a href="#_Latest_Beta_Version_2.00.10">Beta Version 2.00.10</a>
before proceeding with installation and use of this version.</b></p>
<p class=MsoNormal><b>If you are upgrading from a PAMGuard core release
(1.15.xx), PAMGuard Version 2 contains major updates. You should read and
understand the notes listed for <a href="#_Latest_Beta_Version_2.00.10">Beta
Version 2.00.10</a> before proceeding with installation and use of this
version.</b></p>
<p class=MsoNormal>This version of PAMGuard has been bundled with Java 13
(release 13.0.1). PSFX files generated in previous beta releases (2.xx.xx)
@ -1123,8 +1169,8 @@ Bug 441. Plot coordinate calculations incorrect in PamAxis.</p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>10. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span
lang=EN-US> </span>Bug 442. BT Display does not change click symbol color when
Colour By Superdetection is selected.</p>
lang=EN-US> </span>Bug 442. BT Display does not change click symbol color when Colour
By Superdetection is selected.</p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>11. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span
@ -1137,9 +1183,9 @@ Bug 444. Bug in data selector which caused it to mess up history of recent psf
files.</p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>13. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
Bug 445. Overlay data in FX spectrogram display gets out of sync with underlying
spectrogram image.</p>
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span
lang=EN-US> </span>Bug 445. Overlay data in FX spectrogram display gets out of
sync with underlying spectrogram image.</p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>14. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
@ -1148,8 +1194,7 @@ Spectrogram display.</p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>15. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
Bug 447. Viewer mode throws exception when trying to load beamformer
localisations</p>
Bug 447. Viewer mode throws exception when trying to load beamformer localisations</p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>16. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span
@ -1162,8 +1207,8 @@ Bug 449. Rocca Encounter Stats output file calculating incorrect values.</p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>18. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span
lang=EN-US> </span>Bug 450. Ishmael Detectors subscribing to FFTDataBlock
twice, meaning they process each data unit 2x doubling the output.</p>
lang=EN-US> </span>Bug 450. Ishmael Detectors subscribing to FFTDataBlock twice,
meaning they process each data unit 2x doubling the output.</p>
<p class=MsoNormal><b><span lang=EN-US>Upgrades</span></b></p>
@ -1173,9 +1218,9 @@ lang=EN-US> </span>Added functionality to TD display to allow users to manually
classify clicks. </p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>2. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
Added option in Sound Acquisition settings dialog to override filename time
stamp and use PC local time instead. </p>
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span
lang=EN-US> </span>Added option in Sound Acquisition settings dialog to
override filename time stamp and use PC local time instead. </p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>3. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span
@ -1251,9 +1296,9 @@ with installation and use of this version.</span></p>
<p class=MsoNormal><b><span lang=EN-US>Bug Fixes</span></b></p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>1. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
Bug 427. Soundtrap import not closing binary files properly if BCL files do not
contain off-effort 'E' line</p>
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span
lang=EN-US> </span>Bug 427. Soundtrap import not closing binary files properly
if BCL files do not contain off-effort 'E' line</p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>2. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
@ -1393,9 +1438,9 @@ lang=EN-US> </span>Added adaptive noise filter to Ishmael Detectors.</p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>5. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span
lang=EN-US> </span>Many upgrades to the Sound Playback module, including a
high-pass filter, gain control, and the ability to mix wavefrom and envelope data
together to listen to high-frequency clicks and dolphin whistles at the same
time.</p>
high-pass filter, gain control, and the ability to mix wavefrom and envelope
data together to listen to high-frequency clicks and dolphin whistles at the
same time.</p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>6. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
@ -1498,9 +1543,9 @@ Improvements to Difar module graphics - easier reading, better visibility at
night.</p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>7. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
Added print screen button to capture/save all PAMGuard screens to file and log
the information to the database.</p>
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span
lang=EN-US> </span>Added print screen button to capture/save all PAMGuard
screens to file and log the information to the database.</p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>8. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
@ -1551,17 +1596,17 @@ lang=EN-US> </span>Added decimal degrees option to latitude/longitude dialog.</p
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>2. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span
lang=EN-US> </span>Added option in the Click Delay parameters to restrict the
number of initial samples used in the calculation. This can be useful for
cleaning up delays in the presence of echoes and small time delays.</p>
lang=EN-US> </span>Added option in the Click Delay parameters to restrict the number
of initial samples used in the calculation. This can be useful for cleaning up
delays in the presence of echoes and small time delays.</p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>3. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
Increased upsampling to 2, 3 or 4 times.</p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>4. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
Can now change units and scale type in level meter display.</p>
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span
lang=EN-US> </span>Can now change units and scale type in level meter display.</p>
<!-- ************************************************************************************************************************** --><!-- ************************************************************************************************************************** -->
@ -1926,8 +1971,8 @@ User is now able to specify Soundtrap date/time format</p>
<h1><a name="_Latest_Beta_Version_2.00.11"></a><span lang=EN-US>Beta Version
2.00.11 October 2017</span></h1>
<p class=MsoNormal><span lang=EN-US>PAMGuard Version 2 contains major updates.
You should read and understand the notes listed for <a
<p class=MsoNormal><span lang=EN-US>PAMGuard Version 2 contains major updates. You
should read and understand the notes listed for <a
href="#_Latest_Beta_Version_2.00.10">Beta Version 2.00.10</a> before proceeding
with installation and use of this version.</span></p>
@ -1998,9 +2043,9 @@ lang=EN-US> </span>Added 3D rotation to map display. Hold down the shift key
while clicking and dragging on the map to see this in action. </p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>6. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
Added database logging and other updates to the Click Detector trigger function
</p>
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span
lang=EN-US> </span>Added database logging and other updates to the Click
Detector trigger function </p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>7. </span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>
@ -2081,8 +2126,8 @@ to colour them by the colour assigned to the group. </span></p>
<h3><span lang=EN-US>Using Old PAMGuard Configurations</span></h3>
<p class=MsoNormal><span lang=EN-US>Old PAMGuard configurations will work with
the new version. However please note the following:</span></p>
<p class=MsoNormal><span lang=EN-US>Old PAMGuard configurations will work with the
new version. However please note the following:</span></p>
<p class=MsoListParagraph style='margin-left:54.0pt;text-indent:-36.0pt'><span
lang=EN-US>1.</span><span lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
@ -2091,10 +2136,10 @@ so they will no longer work with older PAMGuard versions.</span></p>
<p class=MsoListParagraph style='margin-left:54.0pt;text-indent:-36.0pt'><span
lang=EN-US>2.</span><span lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
</span><span lang=EN-US>Display colour options will be lost and most data
displayed on the map may default to black. This is due to the above changes to
how colours are managed. Changing back to the colours of your choice is
relatively simple through the PAMGuard GUI. </span></p>
</span><span lang=EN-US>Display colour options will be lost and most data displayed
on the map may default to black. This is due to the above changes to how
colours are managed. Changing back to the colours of your choice is relatively
simple through the PAMGuard GUI. </span></p>
<p class=MsoListParagraph style='margin-left:54.0pt;text-indent:-36.0pt'><span
lang=EN-US>&nbsp;</span></p>
@ -2108,8 +2153,8 @@ lang=EN-US>&nbsp;</span></p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>1.</span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
</span><span lang=EN-US>Bug 317. Rocca Module Data Purging. </span>The ROCCA module
was not performing data purging when using classifiers developed for
</span><span lang=EN-US>Bug 317. Rocca Module Data Purging. </span>The ROCCA
module was not performing data purging when using classifiers developed for
Hawaii/Temperate Pacific/North Atlantic datasets. This has been corrected.</p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>2.</span><span
@ -2156,8 +2201,8 @@ list grew to a ridiculous size. Code has been put in place to a) stop it
happening again and b) to repair any configuration files which are corrupted.
Corrupted files will be slow to load, slow to save and will be &gt; several
megabytes in size. It may be necessary to delete the PamguardSettings table in
any databases since these too may have become oversized which will slow down viewer
mode PAMGuard start-up.</p>
any databases since these too may have become oversized which will slow down
viewer mode PAMGuard start-up.</p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>2.</span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
@ -2418,8 +2463,8 @@ detector has been tidied up so that there are a) All Click, b) Tracked Clicks
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
</span><span lang=EN-US>When tracking online, all the click marking information
is written to the same database tables as are used for offline target motion
analysis. This means than when reviewing data offline, the tracks created in
real time are now available for review and further analysis. </span></p>
analysis. This means than when reviewing data offline, the tracks created in real
time are now available for review and further analysis. </span></p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span lang=EN-US>4.</span><span
lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
@ -2462,15 +2507,15 @@ memory that needed to be cleaned up). In some circumstances, these pauses were
making data acquisition systems unstable. We have therefore entirely rewritten
the way in which PAMGuard handles arrays of spectrogram data (complex numbers)
so that instead of large numbers of small Java objects there are now fewer,
larger, simpler java objects. These reduce processing delays for garbage collection
and give an overall speed improvement, but will otherwise not be noticed by
users. </span></p>
larger, simpler java objects. These reduce processing delays for garbage
collection and give an overall speed improvement, but will otherwise not be
noticed by users. </span></p>
<p class=MsoNormal><i><span lang=EN-US>Click Detector RainbowClick file output</span></i></p>
<p class=MsoNormal><span lang=EN-US>This feature has been removed since it has
been obsolete for several years. Users should use the PAMGuard binary storage system
for Click Detector data. </span></p>
been obsolete for several years. Users should use the PAMGuard binary storage
system for Click Detector data. </span></p>
<h1><a name="_Latest_Version_1.15.04"></a><span lang=EN-US>Version 1.15.04 July
2016</span></h1>
@ -2605,8 +2650,8 @@ and datagram creation.</p>
<h1><a name="_Toc444450394"></a><span lang=EN-US>Version 1.15.00 February 2016</span></h1>
<p class=MsoNormal><span lang=EN-US>Beta Version 1.15.00 64 bit and Core version
1.15.00 32 bit. Both using identical Java core software but linking to
<p class=MsoNormal><span lang=EN-US>Beta Version 1.15.00 64 bit and Core
version 1.15.00 32 bit. Both using identical Java core software but linking to
different libraries for control of sound input devices. </span></p>
<p class=MsoNormal><span lang=EN-US>This is the first release of a 64 bit
@ -2688,8 +2733,8 @@ name="_Toc312065299"></a><a name="_Toc312063944"></a><a name="_Toc312065300"></a
name="_Toc312063945"></a>Version 1.14.00 Beta, September 2015</h1>
<p class=MsoNormal>The format of configuration files has changed for version
1.14.00. Older configurations will load with this new version, but configurations
saved with 1.14.00 may not open correctly with earlier versions.</p>
1.14.00. Older configurations will load with this new version, but
configurations saved with 1.14.00 may not open correctly with earlier versions.</p>
<p class=MsoNormal>PAMGuard Versions 1.14.00 and above will work with Java 8.
PAMGuard will continue to work with Java 7, but support for Java 7 will be
@ -2767,8 +2812,8 @@ events. </span></p>
<p class=MsoListParagraph style='margin-left:38.25pt;text-indent:-20.25pt'><span
lang=EN-US>5.</span><span lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
</span><span lang=EN-US>Bug 250. DIFAR module was crashing if it attempted to triangulate
between more than two simultaneous bearings. Fixed. </span></p>
</span><span lang=EN-US>Bug 250. DIFAR module was crashing if it attempted to
triangulate between more than two simultaneous bearings. Fixed. </span></p>
<p class=MsoListParagraph style='margin-left:38.25pt;text-indent:-20.25pt'><span
lang=EN-US>6.</span><span lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
@ -2869,11 +2914,11 @@ which is useful when using PAMGuard for demonstration purposes. </p>
<p class=MsoListParagraph style='margin-left:47.25pt;text-indent:-29.25pt'><span
lang=EN-US>4.</span><span lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
</span>The sound File and Folder audio input systems now have an optional time zone
setting. Note that PAMGuard analysis should still all be taking place in UTC
and that this option is intended to allow the conversion of file times which
were not recorded as UTC into UTC and not the other way around. Use the option
with caution !</p>
</span>The sound File and Folder audio input systems now have an optional time
zone setting. Note that PAMGuard analysis should still all be taking place in
UTC and that this option is intended to allow the conversion of file times
which were not recorded as UTC into UTC and not the other way around. Use the
option with caution !</p>
<p class=MsoListParagraph style='margin-left:47.25pt;text-indent:-29.25pt'><span
lang=EN-US>5.</span><span lang=EN-US style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
@ -2988,8 +3033,9 @@ total loss of the PAMGuard configuration in viewer mode and has been rectified.
7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Bug
218. SAIL Acquisition card would hang the system. This has also been fixed. </p>
<p class=MsoListParagraph style='text-indent:-18.0pt'>7.&nbsp;&nbsp;&nbsp; Bug 219.
Problems displaying Offline Click Events in the Viewer map have been fixed. </p>
<p class=MsoListParagraph style='text-indent:-18.0pt'>7.&nbsp;&nbsp;&nbsp; Bug
219. Problems displaying Offline Click Events in the Viewer map have been
fixed. </p>
<p class=MsoNormal>&nbsp;</p>
@ -3028,9 +3074,8 @@ to read on a time. Fixed</p>
<p class=MsoNormal><i>Menu Layout</i></p>
<p class=MsoNormal>The PAMGuard menus have been rearranged into a more
intuitive grouping which we believe will help users find functionality more
easily. </p>
<p class=MsoNormal>The PAMGuard menus have been rearranged into a more intuitive
grouping which we believe will help users find functionality more easily. </p>
<p class=MsoNormal>'Detection' menu has been renamed to 'Settings' since many
menu items within this menu were not directly to do with 'Detection'.</p>
@ -3087,9 +3132,9 @@ sonobuoys. See online help for details.&nbsp; </p>
<p class=MsoNormal>This module, developed by Jamie Macaulay of St Andrews
University estimates the 3D localisation of clicks using a variety of
algorithms. It's primarily been developed to track harbour porpoise in three
dimensions over scales of 10's of metres. While currently only working with output
from the click detector, we hope eventually to extend its use to whistles as
well. </p>
dimensions over scales of 10's of metres. While currently only working with
output from the click detector, we hope eventually to extend its use to
whistles as well. </p>
<p class=MsoNormal><i>Accelerometer Readout</i> (Sensors group)</p>
@ -3159,10 +3204,11 @@ different. Details are available in the online help. </p>
<p class=MsoNormal><i>FLAC File Support</i></p>
<p class=MsoNormal>Can now read raw audio data direct from FLAC files. <a
href="http://en.wikipedia.org/wiki/FLAC">FLAC</a> is a lossless compression algorithm
for audio data. Files, or folders of files are accessed in the same way as WAV
and AIFF files in the Sound Acquisition module. In a future release we also
hope to provide support for writing FLAC files from the sound recorder module. </p>
href="http://en.wikipedia.org/wiki/FLAC">FLAC</a> is a lossless compression
algorithm for audio data. Files, or folders of files are accessed in the same
way as WAV and AIFF files in the Sound Acquisition module. In a future release
we also hope to provide support for writing FLAC files from the sound recorder
module. </p>
<p class=MsoNormal><i>Sound Recorder Module</i></p>
@ -3175,8 +3221,8 @@ Millisecond time is also now included in the output file names. </p>
<p class=MsoNormal>Datagram options in Viewer have been improved so that the
user has to verify the time binning for datagrams the first time the viewer is
run and can also change the time bins from the File menu (See the File/BinaryStore/Datagram
options menu. </p>
run and can also change the time bins from the File menu (See the
File/BinaryStore/Datagram options menu. </p>
<p class=MsoNormal><i>Viewer Configuration</i></p>
@ -3228,8 +3274,8 @@ whistle.</p>
longer possible to change configurations once PAMGuard has been launched
and pressing 'Cancel' on the select dialog causes PAMGuard to exit. </li>
<li class=MsoNormal style='margin-bottom:0cm'>Airgun display. If this was
included in the PAMGuard model before the GPS module it would hang PAMGuard.
This has been rectified. </li>
included in the PAMGuard model before the GPS module it would hang
PAMGuard. This has been rectified. </li>
<li class=MsoNormal style='margin-bottom:0cm'>Fixed occasional exceptions in
the sound output modules when playing back from files. </li>
<li class=MsoNormal style='margin-bottom:0cm'>Fixed exceptions in spectrogram
@ -3242,8 +3288,8 @@ whistle.</p>
forms which did not display correctly in 'night' mode. </li>
<li class=MsoNormal style='margin-bottom:0cm'>Bug fix in simulator. No longer
stops or fails to start generating sounds. </li>
<li class=MsoNormal style='margin-bottom:0cm'>Bug in calculated spectrum
levels if data were decimated (<a
<li class=MsoNormal style='margin-bottom:0cm'>Bug in calculated spectrum levels
if data were decimated (<a
href="http://sourceforge.net/p/pamguard/bugs/187/">http://sourceforge.net/p/pamguard/bugs/187/</a>)
. Did not affect band level calculations. </li>
<li class=MsoNormal style='margin-bottom:0cm'>Bug in noise band monitor.
@ -3327,9 +3373,9 @@ databases.</p>
<p class=MsoNormal style='margin-left:36.0pt'>National Instruments cards: Added
code in support of the new x-series devices. </p>
<p class=MsoNormal style='margin-left:36.0pt'>ASIO sound cards: Added support
for a new open source ASIO driver system (jasiohost). The old system has been
left in place for now while we assess users response to the newer system. </p>
<p class=MsoNormal style='margin-left:36.0pt'>ASIO sound cards: Added support for
a new open source ASIO driver system (jasiohost). The old system has been left
in place for now while we assess users response to the newer system. </p>
<p class=MsoNormal style='margin-left:36.0pt'><i>AIS</i></p>
@ -3633,10 +3679,10 @@ source, even if that data source is loaded after the FFT module is created.</p>
<p class=MsoNormal>1. Binary storage module. </p>
<p class=MsoNormal>Performs a parallel role to the PAMGAURD database but uses binary
files in a proprietary format which is considerably more efficient for data of
unknown length such as whistle contours or small clips of click waveform. This
feature is currently implemented in the following modules:</p>
<p class=MsoNormal>Performs a parallel role to the PAMGAURD database but uses
binary files in a proprietary format which is considerably more efficient for
data of unknown length such as whistle contours or small clips of click
waveform. This feature is currently implemented in the following modules:</p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span style='font-family:
Symbol'>'</span><span style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
@ -3757,8 +3803,8 @@ channels 0 and 1. Similarly if you switched sound cards, you may have to reconfi
every detector and several of the displays to handle the changes in channel
numbering. </p>
<p class=MsoNormal>I have spent a considerable amount of time trying to work
out a better system for handling channel numbering in PAMGUARD and have decided
<p class=MsoNormal>I have spent a considerable amount of time trying to work out
a better system for handling channel numbering in PAMGUARD and have decided
that the only practical thing to do is to force all software channel numbering
back to a zero indexed system. i.e. even if you read out hardware channels
3,4,5 and 6, within PAMGUARD, everywhere apart from the Sound acquisition
@ -3887,8 +3933,8 @@ frequency versions of the click detector.</p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span style='font-family:
Symbol'>'</span><span style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
</span>Note that this does not (yet) permit simultaneous acquisition and playback
through</p>
</span>Note that this does not (yet) permit simultaneous acquisition and
playback through</p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span style='font-family:
Symbol'>'</span><span style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
@ -4049,9 +4095,9 @@ Symbol'>'</span><span style='font-size:7.0pt;font-family:"Times New Roman",serif
<p class=MsoListParagraph style='text-indent:-18.0pt'><span style='font-family:
Symbol'>'</span><span style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
</span>Channel lists in output data streams of Decimator and other modules
fixed, so that when channel numbers change, downstream modules configurations
get the correct list of available channels. </p>
</span>Channel lists in output data streams of Decimator and other modules fixed,
so that when channel numbers change, downstream modules configurations get the
correct list of available channels. </p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span style='font-family:
Symbol'>'</span><span style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
@ -4083,10 +4129,10 @@ Symbol'>'</span><span style='font-size:7.0pt;font-family:"Times New Roman",serif
<p class=MsoListParagraph style='text-indent:-18.0pt'><span style='font-family:
Symbol'>'</span><span style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
</span>New menu functionality by right clicking on any of the tabs of the main
tab control will allow the user to copy the tab contents to the system clipboard
from where it can be copied into other programs (e.g. Word, Powerpoint,
etc.).Some modules, such as the map, have this implemented in other menus
(right click) and also allow printing.&nbsp; </p>
tab control will allow the user to copy the tab contents to the system
clipboard from where it can be copied into other programs (e.g. Word,
Powerpoint, etc.).Some modules, such as the map, have this implemented in other
menus (right click) and also allow printing.&nbsp; </p>
<p class=MsoListParagraph style='text-indent:-18.0pt'><span style='font-family:
Symbol'>'</span><span style='font-size:7.0pt;font-family:"Times New Roman",serif'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
@ -4346,9 +4392,9 @@ a serial port </p>
<p class=MsoNormal>New Likelihood detector. </p>
<p class=MsoNormal>The likelihood detector module is an implementation of a
likelihood ratio test with flexible algorithms and configuration to estimate
likelihood. It is </p>
<p class=MsoNormal>The likelihood detector module is an implementation of a likelihood
ratio test with flexible algorithms and configuration to estimate likelihood.
It is </p>
<p class=MsoNormal>suitable for detecting both short duration Odontocete clicks
(Sperm, Beaked, etc.) as well as moderate duration Mysticete calls (Humpback,

View File

@ -4,7 +4,7 @@
<groupId>org.pamguard</groupId>
<artifactId>Pamguard</artifactId>
<name>Pamguard Java12+</name>
<version>2.02.06</version>
<version>2.02.07b</version>
<description>Pamguard for Java 12+, using Maven to control dependcies</description>
<url>www.pamguard.org</url>
<organization>

View File

@ -4,7 +4,7 @@
<modelVersion>4.0.0</modelVersion>
<groupId>org.pamguard</groupId>
<artifactId>Pamguard</artifactId>
<version>2.02.06a</version>
<version>2.02.07b</version>
<name>Pamguard Java12+</name>
<description>Pamguard for Java 12+, using Maven to control dependcies</description>
<url>www.pamguard.org</url>

View File

@ -950,15 +950,22 @@ public class AcquisitionProcess extends PamProcess {
/**
* Check it's a single channel and not a channel map.
* This fundamentally messed up the amplitude calculations when the
* channels were > 2 since it was only taking the number of the lowest set
* bit. So if a genuine channel was sent, rather than a channel map with a
* single set channel, it messed up. Have made this function redundant
* and we need to be 100% sure that all amplitude calculations are sent a
* channel number not a bitmap with a single set channel.
* @param channel
* @return single channel if it seemed to be a bitmap.
*/
private int checkSingleChannel(int channel) {
int bitCount = PamUtils.getNumChannels(channel);
if (bitCount > 1 || channel > 32) {
channel = PamUtils.getLowestChannel(channel);
}
return channel;
// int bitCount = PamUtils.getNumChannels(channel);
// if (bitCount > 1 || channel > 32) {
// channel = PamUtils.getLowestChannel(channel);
// }
// return channel;
}
/**
@ -1022,7 +1029,7 @@ public class AcquisitionProcess extends PamProcess {
/**
* Prepares for fast amplitude calculations
* @param channel
* @param channel number i.e. 0 - 31, NOT a bitmap.
*/
public double prepareFastAmplitudeCalculation(int channel) {
channel = checkSingleChannel(channel);
@ -1035,7 +1042,7 @@ public class AcquisitionProcess extends PamProcess {
* for an array of double data
*
* @param rawAmplitude raw amplitude (should be -1 < rawAmplitude < 1)
* @param channel channel number (MUST be a channel, not a sequence number)
* @param channel channel number (MUST be a channel 0 - 31, not a sequence number)
* @return amplitude in dB re 1 uPa.
*/
public double[] rawAmplitude2dB(double[] rawAmplitude, int channel){
@ -1122,7 +1129,7 @@ public class AcquisitionProcess extends PamProcess {
/**
* Converts dB in micropascal to ADC counts on a 0 - 1 scale.
* @param channel channel number.
* @param channel channel number, i.e. channel index 0 - 31 NOT a bitmap.
* @param dBMuPascal db in micropascal
* @return ADC counts on a 0-1 scale.
*/

View File

@ -14,7 +14,7 @@ import org.codehaus.plexus.util.FileUtils;
* <p>
* PamAudioFieManager holds a list of PamAudioFile classes. Each PamAudioFile
* can open a certain type of sound file e.g. flac or raw wav files.
* PamAudioFieManager provides fucntions around the list to open files, provide
* PamAudioFieManager provides functions around the list to open files, provide
* file filters etc.
*
* @author Jamie Macaulay
@ -81,8 +81,16 @@ public class PamAudioFileManager {
}
public boolean isSoundFile(File soundFile, String soundExtension) {
String extension = FileUtils.getExtension(soundFile.getName());
if (soundFile == null) {
return false;
}
String extension = FileUtils.getExtension(soundFile.getName());
if (extension == null) {
return false;
}
extension = extension.toLowerCase();
soundExtension = soundExtension.toLowerCase();
//System.out.println("Sound Extension: " + soundExtension + " File extension: " + extension);
return (soundExtension.equals(extension) || soundExtension.equals("." + extension));
}

View File

@ -4,6 +4,8 @@ import GPS.NavDataSynchronisation;
import PamController.PamController;
import PamguardMVC.PamDataBlock;
import PamguardMVC.PamDataUnit;
import PamguardMVC.dataOffline.OfflineDataLoadInfo;
import pamScrollSystem.ViewLoadObserver;
public class StreamerDataBlock extends PamDataBlock<StreamerDataUnit>{
@ -92,4 +94,8 @@ public class StreamerDataBlock extends PamDataBlock<StreamerDataUnit>{
}
}
public boolean loadViewerData(OfflineDataLoadInfo offlineDataLoadInfo, ViewLoadObserver loadObserver) {
return super.loadViewerData(offlineDataLoadInfo, loadObserver);
}
}

View File

@ -3,6 +3,8 @@ package Array;
import java.sql.Connection;
import java.sql.Types;
import Array.sensors.ArrayParameterType;
import Array.sensors.ArraySensorFieldType;
import Array.streamerOrigin.HydrophoneOriginMethod;
import Array.streamerOrigin.HydrophoneOriginMethods;
import Array.streamerOrigin.HydrophoneOriginSystem;
@ -147,9 +149,16 @@ public class StreamerLogging extends SQLLogging {
* Enable orientation is not saved in the database. It is handy to switch between enabling and disabling orientation for all streamers. Therefore we use the default streamer
* in the array manager to determine if our saved streamers will use their orientation data or not.
*/
Streamer defualtStreamer=ArrayManager.getArrayManager().getCurrentArray().getStreamer(streamer.getStreamerIndex());
Streamer defaultStreamer=ArrayManager.getArrayManager().getCurrentArray().getStreamer(streamer.getStreamerIndex());
// if (defualtStreamer!=null) streamer.setEnableOrientation(ArrayManager.getArrayManager().getCurrentArray().getStreamer(streamer.getStreamerIndex()).isEnableOrientation());
// else streamer.setEnableOrientation(true);
if (defaultStreamer != null) {
ArraySensorFieldType[] fieldTypes = ArraySensorFieldType.values();
for (int i = 0; i < fieldTypes.length; i++) {
ArrayParameterType aType = defaultStreamer.getOrientationTypes(fieldTypes[i]);
streamer.setOrientationTypes(fieldTypes[i], aType);
}
}
StreamerDataUnit sdu = new StreamerDataUnit(timeMilliseconds, streamer);
sdu.setDatabaseIndex(databaseIndex);

View File

@ -159,22 +159,21 @@ public class TMGroupLocInfo implements GroupLocInfo {
private void copySubDetections(SuperDetection parentDataUnit, DetectionGroupOptions detectionGroupOptions) {
synchronized (parentDataUnit.getSubDetectionSyncronisation()) {
int totalUnits = parentDataUnit.getSubDetectionsCount();
int keptUnits = totalUnits;
if (detectionGroupOptions != null) {
if (detectionGroupOptions.getMaxLocalisationPoints() == 0 ||
detectionGroupOptions.getMaxLocalisationPoints() < parentDataUnit.getSubDetectionsCount()) {
keptUnits = detectionGroupOptions.getMaxLocalisationPoints();
}
}
subDetectionList = new Vector<>(keptUnits);
float keepRat = (float) (totalUnits-1) / (float) (keptUnits-1);
for (int i = 0; i < keptUnits; i++) {
int unitIndex = Math.round(i*keepRat);
subDetectionList.add(parentDataUnit.getSubDetection(unitIndex));
ArrayList<PamDataUnit> subDets = parentDataUnit.getSubDetections();
int totalUnits = subDets.size();
int keptUnits = totalUnits;
if (detectionGroupOptions != null) {
if (detectionGroupOptions.getMaxLocalisationPoints() == 0 ||
detectionGroupOptions.getMaxLocalisationPoints() < parentDataUnit.getSubDetectionsCount()) {
keptUnits = detectionGroupOptions.getMaxLocalisationPoints();
}
}
subDetectionList = new Vector<>(keptUnits);
float keepRat = (float) (totalUnits-1) / (float) (keptUnits-1);
for (int i = 0; i < keptUnits; i++) {
int unitIndex = Math.round(i*keepRat);
subDetectionList.add(subDets.get(unitIndex));
}
}

View File

@ -111,15 +111,15 @@ public class GebcoNETCDF {
* @param bin
* @return
*/
double binToValue(double[] valueRange, int nBin, int bin) {
return valueRange[0] + (valueRange[1]-valueRange[0])*(double) bin / (double) (nBin-1);
double binToValue(double[] valueRange, int nBin, double bin) {
return valueRange[0] + (valueRange[1]-valueRange[0])*(double) bin / (double) (nBin);
}
double latBinToValue(int latBin) {
double latBinToValue(double latBin) {
return binToValue(latRange, nLat, latBin);
}
double lonBinToValue(int lonBin) {
double lonBinToValue(double lonBin) {
return binToValue(lonRange, nLon, lonBin);
}
@ -131,9 +131,9 @@ public class GebcoNETCDF {
public MapRasterImage createImage(int[] latRangeBins, int[] lonRangeBins, ColourArray heightColours, ColourArray depthColours, int hop) {
latRangeBins[0] = Math.max(latRangeBins[0], 0);
latRangeBins[1] = Math.min(latRangeBins[1], nLat-1);
latRangeBins[1] = Math.min(latRangeBins[1], nLat);
lonRangeBins[0] = Math.max(lonRangeBins[0], 0);
lonRangeBins[1] = Math.min(lonRangeBins[1], nLon-1);
lonRangeBins[1] = Math.min(lonRangeBins[1], nLon);
hop = Math.max(1, hop);
int nLatBins = (latRangeBins[1]-latRangeBins[0])/hop;
int nLonBins = (lonRangeBins[1]-lonRangeBins[0])/hop;
@ -184,9 +184,10 @@ public class GebcoNETCDF {
double[] latRange = new double[2];
double[] lonRange = new double[2];
double[] edges = {-.5, +.5};
for (int i = 0; i < 2; i++) {
latRange[i] = latBinToValue(latRangeBins[i]);
lonRange[i] = lonBinToValue(lonRangeBins[i]);
latRange[i] = latBinToValue(latRangeBins[i]+edges[i]);
lonRange[i] = lonBinToValue(lonRangeBins[i]+edges[i]);
}
return new MapRasterImage(latRange, lonRange, image);
@ -233,11 +234,14 @@ public class GebcoNETCDF {
public static GebcoNETCDF makeGebcoNCDFFile(File ncFile) {
if (ncFile.exists() == false) {
System.out.println("Bathymetry file " + ncFile.getAbsolutePath() + " cannot be found");
return null;
}
NetcdfFile ncf;
try {
ncf = new NetcdfFile(ncFile, true);
return new GebcoNETCDF(ncf);
GebcoNETCDF gebcoRaster = new GebcoNETCDF(ncf);
// ncf.close();
return gebcoRaster;
} catch (IOException e) {
e.printStackTrace();
}

View File

@ -67,11 +67,11 @@ public class GridSwingPainter {
* now go back and recalculate the latlongs of those pixel values since
* we need the lat longs of those bounds to be more precise.
*/
double pixsOffs = -.5;
pLatMin = lat[0] + (lat[1]-lat[0]) * (double) (nLat-pyMax-pixsOffs) / (nLat-1);
pLatMax = lat[0] + (lat[1]-lat[0]) * (double) (nLat-pyMin-pixsOffs) / (nLat-1);
pLonMin = lon[0] + (lon[1]-lon[0]) * (double) (pxMin+pixsOffs) / (nLon-1);
pLonMax = lon[0] + (lon[1]-lon[0]) * (double) (pxMax+pixsOffs) / (nLon-1);
double pixsOffs = 0;//-.5;
pLatMin = lat[0] + (lat[1]-lat[0]) * (double) (nLat-pyMax-pixsOffs) / (nLat);
pLatMax = lat[0] + (lat[1]-lat[0]) * (double) (nLat-pyMin-pixsOffs) / (nLat);
pLonMin = lon[0] + (lon[1]-lon[0]) * (double) (pxMin+pixsOffs) / (nLon);
pLonMax = lon[0] + (lon[1]-lon[0]) * (double) (pxMax+pixsOffs) / (nLon);
// pxMin = Math.max(0, Math.min(pxMin, lon.length-1));
// pxMax = Math.max(0, Math.min(pxMax, lon.length-1));
// pyMin = Math.max(0, Math.min(pyMin, lat.length-1));

View File

@ -260,11 +260,6 @@ public class PamController implements PamControllerInterface, PamSettings {
new MultiportController(this);
}
// binaryStore = new BinaryStore(this);
ToolTipManager.sharedInstance().setDismissDelay(20000);
guiFrameManager = PamGUIManager.createGUI(this, object);
guiFrameManager.init(); //perform any start up processes for the GUI.

View File

@ -31,12 +31,12 @@ public class PamguardVersionInfo {
* Version number, major version.minorversion.sub-release.
* Note: can't go higher than sub-release 'f'
*/
static public final String version = "2.02.06a";
static public final String version = "2.02.07b";
/**
* Release date
*/
static public final String date = "15 November 2022";
static public final String date = "19 January 2023";
// /**
// * Release type - Beta or Core

View File

@ -247,15 +247,15 @@ public class SelectFolder {
folderName.setColumns(textLength);
}
// public boolean isShowSubFolderOption() {
// return showSubFolderOption;
// }
//
//
// public void setShowSubFolderOption(boolean showSubFolderOption) {
// this.showSubFolderOption = showSubFolderOption;
// setVisibleControls();
// }
public boolean isShowSubFolderOption() {
return showSubFolderOption;
}
public void setShowSubFolderOption(boolean showSubFolderOption) {
this.showSubFolderOption = showSubFolderOption;
setVisibleControls();
}
private void setVisibleControls() {
includeSubFoldersCheckBox.setVisible(showSubFolderOption);

View File

@ -91,6 +91,7 @@ public class ColourScheme implements Serializable, Cloneable {
}
// avoid overflows.
int nCol = whaleColors.length - 1;
// iCol = Math.abs(iCol);
iCol = ((iCol-1)%nCol) + 1;
if (iCol < 0) {
return whaleColors[0];

View File

@ -30,6 +30,12 @@ public class GuiParameters implements Serializable, Cloneable {
private String currentSelectedTab;
/**
* Flag to hide all tool tips - which are
* very annoying when they cover controls you want to use!
*/
private boolean hideAllToolTips = false;
/* (non-Javadoc)
* @see java.lang.Object#clone()
@ -61,4 +67,20 @@ public class GuiParameters implements Serializable, Cloneable {
this.currentSelectedTab = currentSelectedTab;
}
/**
* @return the hideAllToolTips
*/
public boolean isHideAllToolTips() {
return hideAllToolTips;
}
/**
* @param hideAllToolTips the hideAllToolTips to set
*/
public void setHideAllToolTips(boolean hideAllToolTips) {
this.hideAllToolTips = hideAllToolTips;
}
}

View File

@ -23,10 +23,13 @@ package PamView;
import java.awt.BorderLayout;
import java.awt.Component;
import java.awt.Container;
import java.awt.DefaultKeyboardFocusManager;
import java.awt.Desktop;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.Frame;
import java.awt.HeadlessException;
import java.awt.KeyEventDispatcher;
import java.awt.Point;
import java.awt.Rectangle;
import java.awt.Window;
@ -34,6 +37,8 @@ import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.ComponentAdapter;
import java.awt.event.ComponentEvent;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.event.WindowEvent;
@ -46,6 +51,7 @@ import java.net.URL;
import java.util.List;
import javax.swing.ImageIcon;
import javax.swing.JCheckBoxMenuItem;
import javax.swing.JComponent;
import javax.swing.JFrame;
import javax.swing.JLabel;
@ -57,6 +63,8 @@ import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.SwingConstants;
import javax.swing.SwingUtilities;
import javax.swing.Timer;
import javax.swing.ToolTipManager;
import javax.swing.WindowConstants;
import javax.swing.event.ChangeEvent;
import javax.swing.event.ChangeListener;
@ -138,7 +146,7 @@ public class PamGui extends PamView implements WindowListener, PamSettings {
removeModuleEnabler = new MenuItemEnabler();
orderModulesEnabler = new MenuItemEnabler();
frame = new JFrame(getModeName());
frame = new MainFrame(getModeName());
if (FullScreen.isGoFullScreen()) {
// frame.setUndecorated(true);
@ -177,6 +185,7 @@ public class PamGui extends PamView implements WindowListener, PamSettings {
frame.addWindowListener(this);
mainPanel = new PamBorderPanel(new BorderLayout());
mainPanel.setOpaque(true);
mainPanel.addComponentListener(new GUIComponentListener());
@ -251,9 +260,51 @@ public class PamGui extends PamView implements WindowListener, PamSettings {
frame.setVisible(true);
hideToolTips(guiParameters.isHideAllToolTips());
ToolTipManager.sharedInstance().setDismissDelay(20000);
// ToolTipManager.sharedInstance().setReshowDelay(5000);
// System.out.println("Tool tip : getReshowDelay" + ToolTipManager.sharedInstance().getReshowDelay());
// System.out.println("Tool tip : getInitialDelay" + ToolTipManager.sharedInstance().getInitialDelay());
// System.out.println("Tool tip : getDismissDelay" + ToolTipManager.sharedInstance().getDismissDelay());
somethingShowing = true;
}
private class MainFrame extends JFrame implements KeyEventDispatcher {
private static final long serialVersionUID = 1L;
private Timer noTipTimer;
public MainFrame(String title) throws HeadlessException {
super(title);
DefaultKeyboardFocusManager.getCurrentKeyboardFocusManager().addKeyEventDispatcher(this);
noTipTimer = new Timer(6000, new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
hideToolTips(guiParameters.isHideAllToolTips());
noTipTimer.stop();
}
});
}
@Override
public boolean dispatchKeyEvent(KeyEvent e) {
if (e.getKeyCode() == KeyEvent.VK_ESCAPE) {
if (noTipTimer.isRunning()) {
noTipTimer.restart();
}
else {
noTipTimer.start();
}
hideToolTips(true);
}
return false;
}
}
private static volatile boolean somethingShowing = false;
@ -820,6 +871,12 @@ public class PamGui extends PamView implements WindowListener, PamSettings {
menuItem.addActionListener(new ClearHiddenWarnings());
menu.add(menuItem);
JCheckBoxMenuItem hideTips = new JCheckBoxMenuItem("Hide all tool tips", guiParameters.isHideAllToolTips());
hideTips.setToolTipText("<html>Hide annoying pop-up tool tips which keep getting in the way" +
"<br>(or press the Escape key to hide them for 6 seconds)</html>");
hideTips.addActionListener(new HideToolTips(hideTips));
menu.add(hideTips);
/*
* Add menu item to redirect output to file or console screen
*
@ -1173,6 +1230,32 @@ public class PamGui extends PamView implements WindowListener, PamSettings {
}
}
private class HideToolTips implements ActionListener {
private JCheckBoxMenuItem hideTipsCheckbox;
public HideToolTips(JCheckBoxMenuItem hideTips) {
this.hideTipsCheckbox = hideTips;
}
@Override
public void actionPerformed(ActionEvent e) {
boolean shouldHide = !guiParameters.isHideAllToolTips();
hideToolTips(shouldHide);
guiParameters.setHideAllToolTips(shouldHide);
hideTipsCheckbox.setSelected(shouldHide);
}
}
/**
* hide all tool tips
* @param hide
*/
private void hideToolTips(boolean hide) {
ToolTipManager.sharedInstance().setEnabled(!hide);
}
class ClearHiddenWarnings implements ActionListener {
public void actionPerformed(ActionEvent ev){
WarnOnce.clearHiddenList(getGuiFrame());
@ -1250,11 +1333,11 @@ public class PamGui extends PamView implements WindowListener, PamSettings {
/**
* Rewrote the menu enablers for the Logging menu (and made it more general
* to extend to other menus shoule they ever need to be anabled.
* to extend to other menus should they ever need to be enabled).
*
* This arises now that we have multiple main menus on the frame depending on
* which tab is being viewed. Since each menu bar has references to different
* menus and menu items, we can no lnger use the ones set in the constuctors for
* menus and menu items, we can no longer use the ones set in the constructors for
* the menu. Each item is therefore found by name before it's enabled. For now
* I'm taking the names out of the reference to the last menu item.
*
@ -1778,7 +1861,6 @@ public class PamGui extends PamView implements WindowListener, PamSettings {
*/
public boolean restoreSettings(PamControlledUnitSettings pamControlledUnitSettings) {
guiParameters = ((GuiParameters) pamControlledUnitSettings.getSettings()).clone();
return true;
}
public PamTabbedPane getMainTab() {

View File

@ -1237,7 +1237,7 @@ public class PamDataBlock<Tunit extends PamDataUnit> extends PamObservable {
if (offlineDataLoading.isCurrentOfflineLoadKeep()) {
pamDataUnits.add(pamDataUnit);
}
if (shouldBinary && getBinaryDataSource() != null && !isOffline) {
if (shouldBinary && getBinaryDataSource() != null && !isOffline && pamDataUnit.isEmbryonic() == false) {
getBinaryDataSource().saveData(pamDataUnit);
}
}
@ -1311,8 +1311,14 @@ public class PamDataBlock<Tunit extends PamDataUnit> extends PamObservable {
public void updatePamData(Tunit pamDataUnit, long updateTimeMillis) {
pamDataUnit.updateDataUnit(updateTimeMillis);
setChanged();
if (!isOffline) {
if (getBinaryDataSource() != null && getBinaryDataSource().isSaveUpdates()) {
if (!isOffline && pamDataUnit.isEmbryonic() == false) {
/*
* Save it if it't not been saved already or we're saving updates.
* Detectors can keep a dataunit in an embryonic state and add them to the
* datablock so they get displayed, but they will still save when the embryonic
* flag is set false and an update is sent.
*/
if (getBinaryDataSource() != null && (getBinaryDataSource().isSaveUpdates() || pamDataUnit.getDataUnitFileInformation() == null)) {
getBinaryDataSource().saveData(pamDataUnit);
}
}

View File

@ -150,6 +150,13 @@ abstract public class PamDataUnit<T extends PamDataUnit, U extends PamDataUnit>
*/
private boolean forceAmpRecalc = false;
/**
* Flag to say that this is data under development. If this is set true
* then when the data are added to the datablock, they will not get saved
* to the binary store. They will get saved on the first update AFTER the
* embryonic flag is set false.
*/
private boolean embryonic = false;
/**
@ -1689,6 +1696,27 @@ abstract public class PamDataUnit<T extends PamDataUnit, U extends PamDataUnit>
* @return any integer.
*/
public int getColourIndex() {
return (int) getUID();
/*
* This can go wrong when UID > 2^31 since the colour chooser takes
* a mod WRT number of whale colours and it doesn't like negative numbers.
* So need to keep the value going in positive.
*/
long uid = getUID();
uid &= 0x7FFFFFFF; // avoid anything in top bit of an int32 or higher
return (int) uid;
}
/**
* @return the embryonic
*/
public boolean isEmbryonic() {
return embryonic;
}
/**
* @param embryonic the embryonic to set
*/
public void setEmbryonic(boolean embryonic) {
this.embryonic = embryonic;
}
}

View File

@ -368,7 +368,7 @@ public class SuperDetDataBlock<Tunit extends SuperDetection, TSubDet extends Pam
}
if (!found) {
superDet = null;
System.out.printf("Can't find data unit id %d, UID %d in %s\n", superID, superUID, getDataName());
Debug.out.printf("Can't find data unit id %d, UID %d in %s\n", superID, superUID, getDataName());
}
}
if (superDet == null) {
@ -448,6 +448,9 @@ public class SuperDetDataBlock<Tunit extends SuperDetection, TSubDet extends Pam
int iDone = 0;
while (duIt.hasNext()) {
Tunit aData = duIt.next(); // looping through superdetections.
// if (aData.getDatabaseIndex() == 131) {
// System.out.println("On event 131");
// }
if (viewLoadObserver != null) {
viewLoadObserver.sayProgress(1, aData.getTimeMilliseconds(), firstTime, lastTime, iDone++);
}
@ -479,6 +482,7 @@ public class SuperDetDataBlock<Tunit extends SuperDetection, TSubDet extends Pam
sdInfo.setSubDetection(null);
}
}
// aData.weedMissingSubDetections();
}
}
return true;

View File

@ -278,23 +278,28 @@ public class SuperDetection<T extends PamDataUnit> extends PamDataUnit<T, SuperD
* @return an array list of sub detection data units
*/
public ArrayList<PamDataUnit<?,?>> getSubDetections() {
if (subDetections == null) {
return null;
}
ArrayList<PamDataUnit<?,?>> subDets = new ArrayList<>(getSubDetectionsCount());
for (SubdetectionInfo<T> subInfo:subDetections) {
T subDet = subInfo.getSubDetection();
if (subDet == null) {
continue;
synchronized (getSubDetectionSyncronisation()) {
if (subDetections == null) {
return null;
}
subDets.add(subDet);
ArrayList<PamDataUnit<?,?>> subDets = new ArrayList<>(getSubDetectionsCount());
for (SubdetectionInfo<T> subInfo:subDetections) {
T subDet = subInfo.getSubDetection();
if (subDet == null) {
continue;
}
subDets.add(subDet);
}
return subDets;
}
return subDets;
}
public T getSubDetection(int ind) {
synchronized (subDetectionSyncronisation) {
if (subDetections == null) return null;
if (ind >= subDetections.size()) {
return null;
}
return subDetections.get(ind).getSubDetection();
}
}
@ -351,10 +356,15 @@ public class SuperDetection<T extends PamDataUnit> extends PamDataUnit<T, SuperD
if (subDetections == null) {
return null;
}
for (int i=0; i<subDetections.size(); i++) {
T aSub = subDetections.get(i).getSubDetection();
if (aSub.getUID() == UID) {
return aSub;
synchronized (subDetectionSyncronisation) {
for (int i=0; i<subDetections.size(); i++) {
T aSub = subDetections.get(i).getSubDetection();
if (aSub == null) {
continue;
}
if (aSub.getUID() == UID) {
return aSub;
}
}
}
return null;
@ -480,6 +490,24 @@ public class SuperDetection<T extends PamDataUnit> extends PamDataUnit<T, SuperD
}
/**
* Get a list of sub detections which are actually present.
* @return list of sub detections which have a non-null sub data unit.
*/
public List<SubdetectionInfo<T>> getPresentSubDetections() {
ArrayList<SubdetectionInfo<T>> exList = new ArrayList<>(getSubDetectionsCount());
synchronized (getSubDetectionSyncronisation()) {
for (SubdetectionInfo<T> subInf : subDetections) {
if (subInf.getSubDetection() == null) {
continue;
}
exList.add(subInf);
}
exList.trimToSize();
}
return exList;
}
/**
* Get the full list of subdetection info's (which may not all
* have a sub detection in memory)
@ -545,4 +573,21 @@ public class SuperDetection<T extends PamDataUnit> extends PamDataUnit<T, SuperD
}
}
/**
* Remove sub detection infos which have no actual sub detection
* loaded. Don't use since super dets are supposed to keep the full
* list even if they don't have loaded subdets.
*/
// public void weedMissingSubDetections() {
// synchronized (getSubDetectionSyncronisation()) {
// ListIterator<SubdetectionInfo<T>> subInfIter = subDetections.listIterator();
// while (subInfIter.hasNext()) {
// SubdetectionInfo<T> subDetInfo = subInfIter.next();
// if (subDetInfo.getSubDetection() == null) {
// subInfIter.remove();
// }
// }
// }
// }
}

View File

@ -1422,6 +1422,7 @@ Text {
-color-cell-bg-odd: -color-bg-subtle;
-color-cell-border: -color-border-default;
-fx-border-color: -color-cell-border;
-fx-control-inner-background: -color-bg-default;
-fx-border-width: 1px;
-fx-border-radius: 0;
-color-header-bg: -color-bg-subtle;
@ -3703,4 +3704,20 @@ Text {
#label-title2 {
-fx-font: bold 13pt -fx-font-family;
}
/*******************************************************************************
* *
* Label *
* *
******************************************************************************/
.validatorfx-error {
-fx-text-fill: rgb(164, 0, 0);
}
.validatorfx-warning {
-fx-text-fill: rgb(196, 160, 0);
}
}

View File

@ -27,7 +27,11 @@ public class SimpleAlarmCounter extends AlarmCounter {
@Override
public double getValue(int countType, PamDataUnit dataUnit) {
return 1;
if (dataSelector == null) {
return 1;
}
double val = dataSelector.scoreData(dataUnit);
return val;
}
@Override

View File

@ -47,6 +47,8 @@ import java.awt.image.BufferedImage;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.ConcurrentModificationException;
import java.util.HashMap;
import java.util.List;
import java.util.ListIterator;
import javax.swing.JCheckBox;
@ -134,7 +136,7 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
private PamScroller hScrollBar;
// private PamDataBlock<ClickDetection> trackedClicks;
// private PamDataBlock<ClickDetection> trackedClicks;
protected BTPlot btPlot;
@ -219,7 +221,7 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
/**
* The symbol chooser for the BT display
*/
// private ClickDetSymbolChooser symbolChooser;
// private ClickDetSymbolChooser symbolChooser;
public ClickBTDisplay(ClickControl clickControl, ClickDisplayManager clickDisplayManager, ClickDisplayManager.ClickDisplayInfo clickDisplayInfo) {
@ -265,7 +267,7 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
topControls = new TopControls();
setNorthPanel(topControls);
// trackedClicks = clickControl.getClickDetector().getTrackedClicks();
// trackedClicks = clickControl.getClickDetector().getTrackedClicks();
highlightSymbol.setLineThickness(3);
@ -369,13 +371,49 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
@Override
public void updateData(PamObservable observable, PamDataUnit pamDataUnit) {
if (pamDataUnit instanceof ClickDetection) {
updateClick((ClickDetection) pamDataUnit);
}
}
private void updateClick(ClickDetection clickDetection) {
// ICI may have been set when the click was added to an event
// so work it out there rather than rebuilding the entire list.
SuperDetection superDet = clickDetection.getSuperDetection(0);
if (superDet == null) {
// sortTempICIs();
return;
}
/**
* Work only within the superdetection to find the previous
* click within that for this clicks channel combination and update
* the ICI accordingly. For the first click an event, it won't find
* a preceeding click, but that's OK.
*/
synchronized (superDet.getSubDetectionSyncronisation()) {
int subDetInd = superDet.findSubdetectionInfo(clickDetection);
for (int i = subDetInd-1; i >= 0; i--) {
PamDataUnit subDet = superDet.getSubDetection(i);
if (subDet.getChannelBitmap() == clickDetection.getChannelBitmap()) {
double ici = (double) (clickDetection.getTimeMilliseconds() - subDet.getTimeMilliseconds())/1000.;
clickDetection.setTempICI(ici);
break;
}
}
}
}
private void changedEvent(OfflineEventDataUnit event) {
sortTempICIs();
btPlot.repaint(10);
}
public void newClick(ClickDetection clickDataUnit) {
sortTempICI(clickDataUnit);
if (shouldPlot(clickDataUnit)){
// btPlot.drawClick(btPlot.getImageGraphics(), clickDataUnit, null);
// btPlot.repaint(minPaintTime);
@ -386,6 +424,71 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
}
private HashMap<Long, ClickDetection> lastClicks = new HashMap<>();
/**
* Sort out all ICI's for all clicks.
*/
private void sortTempICIs() {
// long t1 = System.nanoTime();
PamDataBlock<ClickDetection> clickData = clickControl.getClickDataBlock();
ArrayList<ClickDetection> allClicks = clickData.getDataCopy();
sortTempICIs(allClicks);
// long t2 = System.nanoTime();
// System.out.printf("time to sort %d ICI measures is %3.1fms\n", allClicks.size(), (double) (t2-t1)/1.e6);
}
/**
* Clear ICI history, e.g. when new data are loaded or processing starts.
*/
private void clearICIHistory() {
synchronized(lastClicks) {
lastClicks.clear();
}
}
/**
* Sorts ICI's for a list of clicks.
* @param clicks
*/
private void sortTempICIs(List<ClickDetection> clicks) {
clearICIHistory();
for (ClickDetection aClick : clicks) {
sortTempICI(aClick);
}
}
/**
* Sorts ICI information for a new click.
* @param aClick
*/
private void sortTempICI(ClickDetection aClick) {
long chans = aClick.getChannelBitmap(); // int32 channel group.
long superId = 0;
SuperDetection superDet = aClick.getSuperDetection(0);
if (superDet != null) {
superId = superDet.getUID();
}
/*
* make an overall id for the click in a long. This could in theory wrap
* a superdet, but that is very unlikely and we probably don't care anyway
* since it's unlikely a uid that different would be in memory at the same time.
*/
long totalId = superId<<32 | chans;
synchronized(lastClicks) {
ClickDetection prevClick = lastClicks.get(totalId);
if (prevClick == null) {
aClick.setTempICI(0);
}
else {
double ici = (double) (aClick.getTimeMilliseconds() - prevClick.getTimeMilliseconds()) / 1000.;
aClick.setTempICI(ici);
}
lastClicks.put(totalId, aClick);
}
}
/**
@ -467,6 +570,8 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
hScrollManager.reset();
}
clearICIHistory();
// hScrollManager.setupScrollBar(0);
// setupTimeBar();
repaintBoth();
@ -1193,6 +1298,8 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
hScrollBar.setUnitIncrement(getUnitIncrement(getTimeRangeMillis()));
hScrollBar.setBlockIncrement(getTimeRangeMillis() * 7 / 8);
sortTempICIs();
return true;
}
@ -1265,7 +1372,7 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
// System.out.println("New max time = " + PamCalendar.formatTime(displayMaxMillis));
// System.out.println(String.format("Set up scroll bar at %s", PamCalendar.formatDateTime(displayMaxMillis)));
long displayLength = getTimeRangeMillis();
// long currentStart = hScrollBar.getMinimumMillis();
// long currentStart = hScrollBar.getMinimumMillis();
long scrollRange = hScrollBar.getRangeMillis(); // total scrollable range
long currentValue = hScrollBar.getValueMillis();
long displayMinMillis = displayMaxMillis-scrollRange; // start of scrollable region.
@ -1444,6 +1551,7 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
@Override
public void offlineDataChanged() {
sortTempICIs();
repaintBoth();
}
@ -1572,9 +1680,9 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
}
private double clickAngleToY(ClickDetection click) {
AbstractLocalisation loc = click.getLocalisation();
// if (click.getUID() == 110006089) {
// System.out.println("Click 110006089 angle " + click.getAngle());
// }
// if (click.getUID() == 110006089) {
// System.out.println("Click 110006089 angle " + click.getAngle());
// }
if (loc == null) return 0;
double angle = 0;
GpsData oll;
@ -1590,20 +1698,20 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
case ArrayManager.ARRAY_TYPE_VOLUME:
PamVector v = getDisplayVector(click);
angle = Math.toDegrees(PamVector.vectorToSurfaceBearing(v));
// PamVector[] vecs = null;
// angle = click.getAngle();
// if (btDisplayParameters.bearingType == BTDisplayParameters.BEARING_FROMVESSEL) {
// PamVector[] vecs = null;
// angle = click.getAngle();
// if (btDisplayParameters.bearingType == BTDisplayParameters.BEARING_FROMVESSEL) {
// have to use real world vectors to get the array rotation vector
// then subtract back off the heading
// vecs = loc.getPlanarAngles()();
// if (vecs == null || vecs.length < 1) {
// return 0;
// }
// angle = Math.toDegrees(PamVector.vectorToSurfaceBearing(vecs[0]));
// oll = click.getOriginLatLong(false);
// if (oll != null) {
// angle -= oll.getHeading();
// }
// vecs = loc.getPlanarAngles()();
// if (vecs == null || vecs.length < 1) {
// return 0;
// }
// angle = Math.toDegrees(PamVector.vectorToSurfaceBearing(vecs[0]));
// oll = click.getOriginLatLong(false);
// if (oll != null) {
// angle -= oll.getHeading();
// }
break;
default:
return 0;
@ -1648,7 +1756,7 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
if (vr != null && vr.length > 0) {
return vr[0];
}
// rotAngles[0] = Math.toRadians(oll.getHeading());
// rotAngles[0] = Math.toRadians(oll.getHeading());
}
else if (rType == BTDisplayParameters.ROTATE_TONORTH) {
PamVector[] vr = loc.getRealWorldVectors();
@ -1656,11 +1764,11 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
return vr[0];
}
}
// if (rotAngles[0] == 0 && rotAngles[1] == 0 && rotAngles[2] == 0) {
// return v;
// }
// PamQuaternion pq = new PamQuaternion(rotAngles[0], rotAngles[1], rotAngles[2]);
// PamVector v2 = PamVector.rotateVector(v, pq);
// if (rotAngles[0] == 0 && rotAngles[1] == 0 && rotAngles[2] == 0) {
// return v;
// }
// PamQuaternion pq = new PamQuaternion(rotAngles[0], rotAngles[1], rotAngles[2]);
// PamVector v2 = PamVector.rotateVector(v, pq);
return v;
}
@ -1677,16 +1785,16 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
return yStart + (yMax-yPos)/yScale;
}
private ClickDetection lastICIClick;
// private ClickDetection lastICIClick;
private double clickICIToY(ClickDetection click) {
if (click.getICI() > 0) {
return btPlot.getHeight() - yAxis.getPosition(click.getICI());
// return click.getICI() * yScale;
}
else {
return btPlot.getHeight() - yAxis.getPosition(click.getTempICI());
// return click.getTempICI() * yScale;
}
// if (click.getTempICI() > 0) {
return btPlot.getHeight() - yAxis.getPosition(click.getTempICI());
// return click.getICI() * yScale;
// }
// else {
// return btPlot.getHeight() - yAxis.getPosition(click.getTempICI());
// // return click.getTempICI() * yScale;
// }
}
@ -1705,8 +1813,8 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
private double getClickWidth(ClickDetection click) {
return (double) click.getSampleDuration() / (double) clickControl.clickParameters.maxLength *
(btDisplayParameters.maxClickLength - btDisplayParameters.minClickLength) +
btDisplayParameters.minClickLength;
(btDisplayParameters.maxClickLength - btDisplayParameters.minClickLength) +
btDisplayParameters.minClickLength;
}
/**
@ -1783,7 +1891,7 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
}
// private JPopupMenu clickPopupMenu = null;
// private JPopupMenu clickPopupMenu = null;
public RangeSpinner rangeSpinner;
@ -1792,20 +1900,20 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
public ClickDetSymbolChooser symbolChooser;
private JPopupMenu getClickPUMenu(ClickDetection click) {
// if (clickPopupMenu == null){
// clickPopupMenu = new JPopupMenu();
// JMenuItem menuItem;
// PamSymbol pamSymbol;
// Color symbolColour;
// for (int i = 0; i < PamColors.getInstance().getNWhaleColours(); i++) {
// menuItem = new JMenuItem(" Whale Train " + i);
// symbolColour = PamColors.getInstance().getWhaleColor(i);
// pamSymbol = new PamSymbol(PamSymbol.SYMBOL_CIRCLE, 12, 12, true, symbolColour, symbolColour);
// menuItem.setIcon(pamSymbol);
// menuItem.addActionListener(new clickPUListener(i));
// clickPopupMenu.add(menuItem);
// }
// }
// if (clickPopupMenu == null){
// clickPopupMenu = new JPopupMenu();
// JMenuItem menuItem;
// PamSymbol pamSymbol;
// Color symbolColour;
// for (int i = 0; i < PamColors.getInstance().getNWhaleColours(); i++) {
// menuItem = new JMenuItem(" Whale Train " + i);
// symbolColour = PamColors.getInstance().getWhaleColor(i);
// pamSymbol = new PamSymbol(PamSymbol.SYMBOL_CIRCLE, 12, 12, true, symbolColour, symbolColour);
// menuItem.setIcon(pamSymbol);
// menuItem.addActionListener(new clickPUListener(i));
// clickPopupMenu.add(menuItem);
// }
// }
/*
* Make a menu based on which whales are currently alive and active and also
* a "new" category at the end ...
@ -1830,7 +1938,7 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
OfflineEventDataUnit clickGroup = it.next();
whaleId = clickGroup.getEventId();
if (click.getSuperDetection(0) == clickGroup) continue;
// if (whaleId == click.getEventId()) continue;
// if (whaleId == click.getEventId()) continue;
biggestId = Math.max(biggestId, whaleId);
menuItem = new JMenuItem("Click Train " + whaleId);
symbolColour = PamColors.getInstance().getWhaleColor(clickGroup.getColourIndex());
@ -1841,9 +1949,9 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
}
whaleId = biggestId + 1;
menuItem = new JMenuItem("New Click Train");
// symbolColour = PamColors.getInstance().getWhaleColor(whaleId);
// pamSymbol = new PamSymbol(PamSymbol.SYMBOL_CIRCLE, 12, 12, true, symbolColour, symbolColour);
// menuItem.setIcon(pamSymbol);
// symbolColour = PamColors.getInstance().getWhaleColor(whaleId);
// pamSymbol = new PamSymbol(PamSymbol.SYMBOL_CIRCLE, 12, 12, true, symbolColour, symbolColour);
// menuItem.setIcon(pamSymbol);
menuItem.addActionListener(new clickPUListener(whaleId));
clickPopupMenu.add(menuItem, 0);
@ -1861,9 +1969,9 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
if (nEvents >= 2 && clickEvent != null) {
// >= 2 since if there is only one i tmust be this one.
JMenu reassignMenu = new JMenu("Reassign train " + click.getEventId() + " to");
symbolColour = PamColors.getInstance().getWhaleColor(clickEvent.getColourIndex());
pamSymbol = new PamSymbol(PamSymbolType.SYMBOL_CIRCLE, 12, 12, true, symbolColour, symbolColour);
reassignMenu.setIcon(pamSymbol);
symbolColour = PamColors.getInstance().getWhaleColor(clickEvent.getColourIndex());
pamSymbol = new PamSymbol(PamSymbolType.SYMBOL_CIRCLE, 12, 12, true, symbolColour, symbolColour);
reassignMenu.setIcon(pamSymbol);
it = trackedClickGroups.getListIterator(0);
while (it.hasNext()) {
OfflineEventDataUnit clickGroup = it.next();
@ -1921,7 +2029,7 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
if (popupClick == null) return;
// popupClick.setEventId(whaleId);
// popupClick.setEventId(whaleId);
trackClick(popupClick, whaleId);
@ -1962,7 +2070,7 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
private void trackClick(ClickDetection click, int whaleId) {
click.setTracked(true);
// clickControl.clickDetector.reWriteClick(click, false);
// clickControl.clickDetector.reWriteClick(click, false);
// ClickDetection newDataUnit = new ClickDetection(click.getChannelBitmap(), click.getStartSample(),
// click.getDuration(), click.clickDetector, click.triggerList);
@ -2000,35 +2108,35 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
if (scaleManager == null) {
return;
}
// scaleManager
// System.out.println(String.format("set y range from %s %3.4f to %3.4fs", scaleManager.getTitle(),
// scaleManager.getCurrentStart(), scaleManager.getCurrentEnd()));
// scaleManager
// System.out.println(String.format("set y range from %s %3.4f to %3.4fs", scaleManager.getTitle(),
// scaleManager.getCurrentStart(), scaleManager.getCurrentEnd()));
yAxis.setRange(scaleManager.getCurrentStart(), scaleManager.getCurrentEnd());
yAxis.setLogScale(btDisplayParameters.logICIScale && btDisplayParameters.VScale == BTDisplayParameters.DISPLAY_ICI);
yAxis.setInterval(scaleManager.getYAxisInterval());
yAxis.setLabel(scaleManager.getTitle());
yAxis.setAutoFormat(false);
// String format = getYAxisFormat()
// double range = Math.abs(scaleManager.currentRange);
// if (range > 30) {
// yAxis.setFormat("%d");
// }
// else if (range > 8) {
// yAxis.setFormat("%3.1f");
// }
// else if (range > 1) {
// yAxis.setFormat("%3.1f");
// }
// else if (range > .1) {
// yAxis.setFormat("%3.2f");
// }
// else if (range <= 0) {
// yAxis.setFormat("%3.2f");
// }
// else {
// int nDP = (int)Math.ceil(Math.abs(Math.log10(range)));
// yAxis.setFormat(String.format("%%%d.%df", nDP+2, nDP));
// }
// String format = getYAxisFormat()
// double range = Math.abs(scaleManager.currentRange);
// if (range > 30) {
// yAxis.setFormat("%d");
// }
// else if (range > 8) {
// yAxis.setFormat("%3.1f");
// }
// else if (range > 1) {
// yAxis.setFormat("%3.1f");
// }
// else if (range > .1) {
// yAxis.setFormat("%3.2f");
// }
// else if (range <= 0) {
// yAxis.setFormat("%3.2f");
// }
// else {
// int nDP = (int)Math.ceil(Math.abs(Math.log10(range)));
// yAxis.setFormat(String.format("%%%d.%df", nDP+2, nDP));
// }
// switch (btDisplayParameters.VScale) {
//
@ -2227,7 +2335,7 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
* @return
*/
private JPopupMenu getPopupMenu(ClickDetection clickedClick) {
// System.out.println("Create click right click menu.....");
// System.out.println("Create click right click menu.....");
boolean isView = PamController.getInstance().getRunMode() == PamController.RUN_PAMVIEW;
JPopupMenu menu = new JPopupMenu();
JMenuItem menuItem;
@ -2264,8 +2372,8 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
//uurgh...what??
if (sd instanceof GroupDetection) {
menuItem = clickControl.getTargetMotionLocaliser().getEventMenuItem((GroupDetection) sd, "Click Train");
menu.add(menuItem);
}
menu.add(menuItem);
}
}
}
@ -2289,23 +2397,23 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
menu.addSeparator();
}
// menuItem = new JCheckBoxMenuItem("Colour by species id",
// btDisplayParameters.colourScheme == BTDisplayParameters.COLOUR_BY_SPECIES);
// menuItem.addActionListener(new ColourByAction(BTDisplayParameters.COLOUR_BY_SPECIES));
// menu.add(menuItem);
// menuItem = new JCheckBoxMenuItem("Colour by click train",
// btDisplayParameters.colourScheme == BTDisplayParameters.COLOUR_BY_TRAIN);
// menuItem.addActionListener(new ColourByAction(BTDisplayParameters.COLOUR_BY_TRAIN));
// menu.add(menuItem);
// menuItem = new JCheckBoxMenuItem("Colour by train, then species",
// btDisplayParameters.colourScheme == BTDisplayParameters.COLOUR_BY_TRAINANDSPECIES);
// menuItem.addActionListener(new ColourByAction(BTDisplayParameters.COLOUR_BY_TRAINANDSPECIES));
// menu.add(menuItem);
// // if (isNetReceiver) {
// menuItem = new JCheckBoxMenuItem("Colour by hydrophone",
// btDisplayParameters.colourScheme == BTDisplayParameters.COLOUR_BY_HYDROPHONE);
// menuItem.addActionListener(new ColourByAction(BTDisplayParameters.COLOUR_BY_HYDROPHONE));
// menu.add(menuItem);
// menuItem = new JCheckBoxMenuItem("Colour by species id",
// btDisplayParameters.colourScheme == BTDisplayParameters.COLOUR_BY_SPECIES);
// menuItem.addActionListener(new ColourByAction(BTDisplayParameters.COLOUR_BY_SPECIES));
// menu.add(menuItem);
// menuItem = new JCheckBoxMenuItem("Colour by click train",
// btDisplayParameters.colourScheme == BTDisplayParameters.COLOUR_BY_TRAIN);
// menuItem.addActionListener(new ColourByAction(BTDisplayParameters.COLOUR_BY_TRAIN));
// menu.add(menuItem);
// menuItem = new JCheckBoxMenuItem("Colour by train, then species",
// btDisplayParameters.colourScheme == BTDisplayParameters.COLOUR_BY_TRAINANDSPECIES);
// menuItem.addActionListener(new ColourByAction(BTDisplayParameters.COLOUR_BY_TRAINANDSPECIES));
// menu.add(menuItem);
// // if (isNetReceiver) {
// menuItem = new JCheckBoxMenuItem("Colour by hydrophone",
// btDisplayParameters.colourScheme == BTDisplayParameters.COLOUR_BY_HYDROPHONE);
// menuItem.addActionListener(new ColourByAction(BTDisplayParameters.COLOUR_BY_HYDROPHONE));
// menu.add(menuItem);
// }
menuItem = new JCheckBoxMenuItem("Bearing / Time");
menuItem.addActionListener(new AxesMenuAction(BTDisplayParameters.DISPLAY_BEARING));
@ -2639,38 +2747,38 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
}
}
// class ColourByAction implements ActionListener {
//
// private int colourChoice;
//
// public ColourByAction(int colourChoice) {
// super();
// this.colourChoice = colourChoice;
// }
// public void actionPerformed(ActionEvent e) {
// btDisplayParameters.colourScheme = colourChoice;
// symbolChooser.setSymbolType(colourChoice);
//
// btPlot.setTotalRepaint();
// btPlot.repaint(minPaintTime);
// btPlot.createKey();
// }
// }
// class ColourByAction implements ActionListener {
//
// private int colourChoice;
//
// public ColourByAction(int colourChoice) {
// super();
// this.colourChoice = colourChoice;
// }
// public void actionPerformed(ActionEvent e) {
// btDisplayParameters.colourScheme = colourChoice;
// symbolChooser.setSymbolType(colourChoice);
//
// btPlot.setTotalRepaint();
// btPlot.repaint(minPaintTime);
// btPlot.createKey();
// }
// }
class SettingsMenuAction implements ActionListener {
public void actionPerformed(ActionEvent e) {
BTDisplayParameters newParameters =
ClickDisplayDialog.showDialog(clickControl,
clickControl.getPamView().getGuiFrame(), btDisplayParameters);
ClickDisplayDialog.showDialog(clickControl,
clickControl.getPamView().getGuiFrame(), btDisplayParameters);
if (newParameters != null){
btDisplayParameters = newParameters.clone();
if (getVScaleManager() != null) {
getVScaleManager().setSelected();
}
btAxis.makeAxis();
// System.out.println("360: "+btDisplayParameters.view360);
// System.out.println("360: "+btDisplayParameters.view360);
repaintBoth();
btPlot.createKey();
if (clickControl.getOfflineToolbar() != null) {
@ -2694,16 +2802,16 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
Rectangle b = null ;
if (btAmplitudeSelector != null) {
b= btAmplitudeSelector.getFrame().getBounds();
// btAmplitudeSelector.getFrame().setVisible(true);
// // btAmplitudeSelector.getFrame().
// btAmplitudeSelector.getFrame().setVisible(true);
// // btAmplitudeSelector.getFrame().
}
// else {
btAmplitudeSelector = BTAmplitudeSelector.showAmplitudeFrame(clickControl, this);
if(b!=null){
// else {
btAmplitudeSelector = BTAmplitudeSelector.showAmplitudeFrame(clickControl, this);
if(b!=null){
btAmplitudeSelector.getFrame().setBounds(b);
}
// }
btAmplitudeSelector.getFrame().setBounds(b);
}
// }
}
private void checkBTAmplitudeSelectHisto() {
@ -2895,7 +3003,7 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
public boolean redrawAllClicks(){
// System.out.println("redrawAllClicks " + hScrollBar.getValueMillis()+ " "+vScrollBar.getValue()+" "+ hScrollBar.getMaximumMillis()+" "+hScrollBar.getStepSizeMillis());
// System.out.println("redrawAllClicks " + hScrollBar.getValueMillis()+ " "+vScrollBar.getValue()+" "+ hScrollBar.getMaximumMillis()+" "+hScrollBar.getStepSizeMillis());
if (totalRepaint) {
return true;
}
@ -2914,7 +3022,7 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
}
}
// double lastPaintTime;
// double lastPaintTime;
public void paintClicks(Graphics g, Rectangle clipRectangle) {
long t0 = System.nanoTime();
@ -2928,18 +3036,21 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
zoomer.paintShape(g, this, true);
}
// long t1 = System.nanoTime();
// long t1 = System.nanoTime();
synchronized (clickData.getSynchLock()) {
// long t2 = System.nanoTime();
// double ms = ((double) (t2-t1)) / 1000000.;
// long t2 = System.nanoTime();
// double ms = ((double) (t2-t1)) / 1000000.;
// if (btDisplayParameters.VScale == BTDisplayParameters.DISPLAY_ICI) {
// sortTempICIs();
// }
ListIterator<ClickDetection> clickIterator = clickData.getListIterator(PamDataBlock.ITERATOR_END);
while (clickIterator.hasPrevious()) {
click = clickIterator.previous();
if (shouldPlot(prevPlottedClick)){
if (btDisplayParameters.VScale == BTDisplayParameters.DISPLAY_ICI) {
prevPlottedClick.setTempICI((double) (prevPlottedClick.getStartSample()-click.getStartSample()) / sampleRate);
}
// if (btDisplayParameters.VScale == BTDisplayParameters.DISPLAY_ICI) {
// prevPlottedClick.setTempICI((double) (prevPlottedClick.getStartSample()-click.getStartSample()) / sampleRate);
// }
if (drawClick(g, prevPlottedClick, clipRectangle) < -0){
break;
}
@ -2949,16 +3060,16 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
if (shouldPlot(prevPlottedClick)){ // and draw the last one !
drawClick(g, prevPlottedClick, clipRectangle);
}
// g.drawString(String.format("Wait synch %3.3fms", ms), 0, 20);
// g.drawString(String.format("Wait synch %3.3fms", ms), 0, 20);
}
// long t3 = System.nanoTime();
// g.drawString(String.format("Last draw %3.3fms", lastPaintTime), 0, 20);
// lastPaintTime = ((double) (t3-t0)) / 1000000.;
// long t3 = System.nanoTime();
// g.drawString(String.format("Last draw %3.3fms", lastPaintTime), 0, 20);
// lastPaintTime = ((double) (t3-t0)) / 1000000.;
}
@Override
public void paintPanel(Graphics g, Rectangle clipRectangle) {
// long tNow = System.currentTimeMillis();
// long tNow = System.currentTimeMillis();
redrawClicks=redrawAllClicks();
/**
* Need to call this every time since the original symbol chooser will get deleted after
@ -3090,14 +3201,14 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
if (pt.x - width > clipRegion.x + clipRegion.width) return +1;
}
if (click.tracked) {
// System.out.println("Drawing tracked click");
// System.out.println("Drawing tracked click");
}
//set the colour scheme.
// symbolChooser.setSymbolType(btDisplayParameters.colourScheme);
// symbolChooser.setSymbolType(btDisplayParameters.colourScheme);
PamSymbol symbol = symbolChooser.getPamSymbol(btProjector, click);
//.getClickSymbol(clickControl.getClickIdentifier(), click, btDisplayParameters.colourScheme);
//.getClickSymbol(clickControl.getClickIdentifier(), click, btDisplayParameters.colourScheme);
symbol.setFill(!click.isEcho());
symbol.draw(g, pt, width, height);
@ -3156,8 +3267,8 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
return null;
}
String tip = click.getSummaryString();
// String tip = String.format("<html>UID. %d; Click No. %d; Channels %s", click.getUID(),
// click.clickNumber, PamUtils.getChannelList(click.getChannelBitmap()));
// String tip = String.format("<html>UID. %d; Click No. %d; Channels %s", click.getUID(),
// click.clickNumber, PamUtils.getChannelList(click.getChannelBitmap()));
byte type = click.getClickType();
if (clickControl.getClickIdentifier() != null) {
String typeStr = clickControl.getClickIdentifier().getSpeciesName(type);
@ -3258,11 +3369,11 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
}
setKeyPanel(keyPanel);
try {
keyPanel.getTitledBorder().setTitleColor(PamColors.getInstance().getColor(PamColor.AXIS));
setKeyPosition(CornerLayoutContraint.LAST_LINE_START);
keyPanel.getTitledBorder().setTitleColor(PamColors.getInstance().getColor(PamColor.AXIS));
setKeyPosition(CornerLayoutContraint.LAST_LINE_START);
}
catch (NullPointerException e) {
// e.printStackTrace();
// e.printStackTrace();
}
}
@ -3342,7 +3453,7 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
return false;
}
if (btDisplayParameters.VScale == BTDisplayParameters.DISPLAY_ICI) {
// if (btDisplayParameters.showUnassignedICI == false && click.getICI() < 0) return false;
// if (btDisplayParameters.showUnassignedICI == false && click.getICI() < 0) return false;
if (btDisplayParameters.showUnassignedICI == false && click.getSuperDetectionsCount() <= 0) return false;
// otherwise may be ok, since will estimate all ici's on teh fly.
}
@ -3436,7 +3547,7 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
* to zero. However DO call these functions which were previously in
* reset();
*/
// reset();
// reset();
int channels = clickControl.clickParameters.getChannelBitmap();
int[] channelGroups = clickControl.clickParameters.getChannelGroups();
int nChannelGroups = GroupedSourcePanel.countChannelGroups(channels, channelGroups);
@ -3502,8 +3613,8 @@ public class ClickBTDisplay extends ClickDisplay implements PamObserver, PamSett
this.btDisplayParameters = ((BTDisplayParameters) pamControlledUnitSettings
.getSettings()).clone();
// rangeScrollBar.setValue(btDisplayParameters.vScrollValue);
// rangeSpinner.setSpinnerValue(btDisplayParameters.getTimeRange());
// btPlot.createKey();
// rangeSpinner.setSpinnerValue(btDisplayParameters.getTimeRange());
// btPlot.createKey();
return true;
}

View File

@ -412,7 +412,7 @@ public class SweepClassifier implements ClickIdentifier , PamSettings {
}
@Override
public ClassifyPaneFX getClassifierPane() {
public SweepClassifierPaneFX getClassifierPane() {
if (fxPane==null) fxPane = new SweepClassifierPaneFX(this, clickControl);
return fxPane;
}

View File

@ -1511,7 +1511,7 @@ public class ClickDetection extends PamDataUnit<PamDataUnit, PamDataUnit> implem
* @param iCI the iCI to set
*/
public void setICI(double iCI) {
ICI = iCI;
this.ICI = iCI;
}
protected void setChannelGroupDetector(ChannelGroupDetector channelGroupDetector) {

View File

@ -40,6 +40,7 @@ import pamViewFX.fxNodes.PamVBox;
import pamViewFX.fxNodes.pamDialogFX.PamDialogFX;
import pamViewFX.fxNodes.utilityPanes.FilterPaneFX;
import pamViewFX.fxNodes.utilityPanes.GroupedSourcePaneFX;
import pamViewFX.validator.PamValidator;
/**
* A pane to change click detector settings.
@ -175,7 +176,7 @@ public class ClickSettingsPane extends SettingsPane<ClickParameters>{
/**
* The default pane width
*/
public static double PREF_PANE_WIDTH=550;
public static double PREF_PANE_WIDTH=560;
/**
@ -190,7 +191,7 @@ public class ClickSettingsPane extends SettingsPane<ClickParameters>{
this.clickControl=clickControl;
mainPane= new PamBorderPane();
clickValidator = new Validator();
clickValidator = new PamValidator();
pamTabbedPane=new PamTabPane();
pamTabbedPane.setAddTabButton(false);

View File

@ -284,5 +284,17 @@ public class OfflineEventDataBlock extends SuperDetDataBlock<OfflineEventDataUni
return (clickDetector.getClickDataBlock() == subDataBlock || clickDetector.getTrackedClicks() == subDataBlock);
}
// int nName = 0;
// @Override
// public String getDataName() {
// // TODO Auto-generated method stub
// System.out.println("Call into getDataName " + ++nName);
// if (nName == 58) {
//
// System.out.println("Call into getDataName " + ++nName);
// }
// return super.getDataName();
// }
}

View File

@ -164,15 +164,14 @@ public class OfflineToolbar {
return;
}
String[] speciesList = clickId.getSpeciesList();
if (speciesList == null || speciesList.length == 0) {
return;
}
speciesButtons = new JCheckBox[speciesList.length];
for (int i = 0; i < speciesList.length; i++) {
speciesButtons[i] = new SpeciesCheckBox(speciesList[i] + space);
c.gridx++;
speciesBar.add(speciesButtons[i]);
speciesButtons[i].addActionListener(showClicks);
if (speciesList != null) {
speciesButtons = new JCheckBox[speciesList.length];
for (int i = 0; i < speciesList.length; i++) {
speciesButtons[i] = new SpeciesCheckBox(speciesList[i] + space);
c.gridx++;
speciesBar.add(speciesButtons[i]);
speciesButtons[i].addActionListener(showClicks);
}
}
c.gridx++;
speciesBar.add(andOrSelection = new JComboBox<String>());

View File

@ -619,9 +619,11 @@ public class ModuleConnectionNode extends StandardConnectionNode implements PAMC
//add tool tip
if (pamControlledUnit!=null){
Tooltip tp = new Tooltip(pamControlledUnit.getUnitType());
tp.getStyleClass().removeAll(tp.getStyleClass());
Tooltip.install(this, tp);
//sometimes seems to cause an issue woith dialogs disappearing.
// Tooltip tp = new Tooltip(pamControlledUnit.getUnitType());
// tp.getStyleClass().removeAll(tp.getStyleClass());
// Tooltip.install(this, tp);
//if no way for input then remove socket.
if (!hasInput(pamControlledUnit)){

View File

@ -25,6 +25,9 @@ import pamViewFX.symbol.StandardSymbolOptionsPane;
*/
public class GenericSettingsPane extends PamBorderPane implements TDSettingsPane {
/**
*
*/
private static final double PREF_WIDTH = 300;
/*

View File

@ -61,6 +61,7 @@ public class LandmarkControl extends PamControlledUnit implements PamSettings {
public boolean restoreSettings(PamControlledUnitSettings pamControlledUnitSettings) {
landmarkDatas = ((LandmarkDatas) pamControlledUnitSettings.getSettings()).clone();
landmarkDataBlock.createDataUnits(landmarkDatas);
return true;
}

View File

@ -4,7 +4,9 @@ import PamUtils.PamCalendar;
import PamView.symbol.StandardSymbolManager;
import PamguardMVC.PamDataBlock;
import PamguardMVC.PamProcess;
import PamguardMVC.dataOffline.OfflineDataLoadInfo;
import autecPhones.AutecGraphics;
import pamScrollSystem.ViewLoadObserver;
public class LandmarkDataBlock extends PamDataBlock<LandmarkDataUnit> {
@ -31,4 +33,14 @@ public class LandmarkDataBlock extends PamDataBlock<LandmarkDataUnit> {
}
}
@Override
public boolean loadViewerData(long dataStart, long dataEnd, ViewLoadObserver loadObserver) {
return true;
}
@Override
public boolean loadViewerData(OfflineDataLoadInfo offlineDataLoadInfo, ViewLoadObserver loadObserver) {
return true;
}
}

View File

@ -128,22 +128,27 @@ public class LevelMeterSidePanel extends PamObserverAdapter implements PamSidePa
levelDisplays[i].setLimits(levelMeterControl.levelMeterParams.minLevel, 0);
}
checkConstants();
}
private void checkConstants() {
// now find the source acquisition module and any gain that's in between them.
PamRawDataBlock rawBlock = (PamRawDataBlock) parentBlock;
if (rawBlock!=null) {
AcquisitionProcess daqProcess = (AcquisitionProcess) rawBlock.getSourceProcess();
AcquisitionControl daqControl = daqProcess.getAcquisitionControl();
voltsPeak2Peak = daqControl.acquisitionParameters.voltsPeak2Peak;
int nChan = PamUtils.getNumChannels(channelMap);
maxFullScale = Double.NEGATIVE_INFINITY;
for (int i = 0; i < nChan; i++) {
int chan = PamUtils.getNthChannel(i, channelMap);
gains[chan] = rawBlock.getDataGain(chan);
dbFullScale[chan] = daqProcess.rawAmplitude2dB(1, chan, false);
maxFullScale = Math.max(maxFullScale, dbFullScale[chan]);
}
setupLabels();
if (rawBlock==null) {
return;
}
int channelMap = parentBlock.getChannelMap();
AcquisitionProcess daqProcess = (AcquisitionProcess) rawBlock.getSourceProcess();
AcquisitionControl daqControl = daqProcess.getAcquisitionControl();
voltsPeak2Peak = daqControl.acquisitionParameters.voltsPeak2Peak;
int nChan = PamUtils.getNumChannels(channelMap);
maxFullScale = Double.NEGATIVE_INFINITY;
for (int i = 0; i < nChan; i++) {
int chan = PamUtils.getNthChannel(i, channelMap);
gains[chan] = rawBlock.getDataGain(chan);
dbFullScale[chan] = daqProcess.rawAmplitude2dB(1, chan, false);
maxFullScale = Math.max(maxFullScale, dbFullScale[chan]);
}
setupLabels();
}
private void setupLabels() {
@ -228,7 +233,7 @@ public class LevelMeterSidePanel extends PamObserverAdapter implements PamSidePa
case LevelMeterParams.DISPLAY_VOLTS:
return 20.*Math.log10(level*(voltsPeak2Peak/2));
case LevelMeterParams.DISPLAY_MICROPASCAL:
return 20.*Math.log10(level) + maxFullScale;
return 20.*Math.log10(level) + dbFullScale[channel];
}
return 0;
}

View File

@ -30,6 +30,7 @@ import javax.swing.text.MaskFormatter;
import Array.ArrayManager;
import GPS.GPSControl;
import GPS.GPSDataBlock;
import GPS.GpsData;
import GPS.GpsDataUnit;
import NMEA.NMEADataBlock;
import NMEA.NMEADataUnit;
@ -657,97 +658,24 @@ public class LatLongControl extends LoggerControl implements ClipboardOwner{
}
// private class LatChangeListener implements PropertyChangeListener{
//
// /* (non-Javadoc)
// * @see java.beans.PropertyChangeListener#propertyChange(java.beans.PropertyChangeEvent)
// */
// @Override
// public void propertyChange(PropertyChangeEvent arg0) {
//
// System.out.println("old:"+arg0.getOldValue());
// System.out.println("new:"+arg0.getNewValue());
// try {
// textFieldLat.commitEdit();
// } catch (ParseException e) {
// // TODO Auto-generated catch block
//// e.printStackTrace();
// }
// }
//
// }
// private class LonChangeListener implements PropertyChangeListener{
//
// /* (non-Javadoc)
// * @see java.beans.PropertyChangeListener#propertyChange(java.beans.PropertyChangeEvent)
// */
// @Override
// public void propertyChange(PropertyChangeEvent arg0) {
//
//// System.out.println("old:"+arg0.getOldValue());
//// System.out.println("new:"+arg0.getNewValue());
// try {
// textFieldLon.commitEdit();
// } catch (ParseException e) {
// // TODO Auto-generated catch block
//// e.printStackTrace();
// }
// }
//
// }
@Override
public void setData(Object latLong) {
LatLong a = (LatLong)latLong;
if (a==null){
if (latLong==null || latLong instanceof LatLong == false){
// System.out.println("latLon null");
textFieldLat.setValue(null);
textFieldLon.setValue(null);
return;
}
LatLong a = (LatLong)latLong;
// System.out.println("a :"+a.toString());
textFieldLat.setValue(a.getLatitude());
// textFieldLat.setText(a.formatLatitude());
// System.out.println("a latVal:"+textFieldLat.getValue());
// System.out.println("a latTxt:"+textFieldLat.getText());
textFieldLon.setValue(a.getLongitude());
// textFieldLon.setText(a.formatLongitude());
// addPropertyChangeListener("value", this);
// try {
// textFieldLat.commitEdit();
// textFieldLon.commitEdit();
// } catch (ParseException e) {
// if (dataWarning==null) dataWarning="";
// dataWarning+=" Unable to setData(...) ";
// e.printStackTrace();
// }
// if (latLong==null){
// System.out.println("LatLont null");
// textFieldLat.setText("");
// textFieldLon.setText("");
// return;
// }
//
// if (latLong.getClass().isAssignableFrom(LatLong.class)){
// System.out.println("LatLont assignable");
// LatLong latLon = (LatLong) latLong;
//
// if (latLon==null){
// System.out.println("LatLont still null");
// textFieldLat.setText("");
// textFieldLon.setText("");
// return;
// }
//
// textFieldLat.setText(LatLong.formatLatitude(latLon.getLatitude()));
// System.out.println(latLon.toString());
// textFieldLon.setText(LatLong.formatLongitude(latLon.getLongitude()));
// }
}
@ -856,6 +784,15 @@ public class LatLongControl extends LoggerControl implements ClipboardOwner{
try {
GpsDataUnit gpsUnit = findGpsDataBlock().getLastUnit();
if (gpsUnit == null) {
setData(null);
return AUTO_UPDATE_FAIL;
}
GpsData gpsData = gpsUnit.getGpsData();
if (gpsData == null) {
setData(null);
return AUTO_UPDATE_FAIL;
}
latitude = gpsUnit.getGpsData().getLatitude();
longitude = gpsUnit.getGpsData().getLongitude();

View File

@ -161,7 +161,8 @@ public class NoiseBandProcess extends PamProcess {
lastOutputTime = timeMillis;
}
else if (timeMillis - lastOutputTime >= noiseBandControl.noiseBandSettings.outputIntervalSeconds*1000) {
daqProcess.prepareFastAmplitudeCalculation(iChan);
double ampTerm = daqProcess.prepareFastAmplitudeCalculation(iChan);
// System.out.printf("Amplitude term cahnnel %d is %3.1f\n", iChan, ampTerm);
double[][] measurementStats = new double[bandOutputs.length][2];
for (int i = 0; i < bandOutputs.length; i++) {
measurementStats[bandOutputs.length-i-1][0] = daqProcess.rawAmplitude2dB(bandOutputs[i].getRMS(), iChan, true);

View File

@ -140,6 +140,7 @@ public class PamScrollSlider extends AbstractPamScrollerAWT {
valueMillis = Math.max(scrollerData.minimumMillis, Math.min(scrollerData.maximumMillis, valueMillis));
int val = (int) ((valueMillis - scrollerData.minimumMillis) / scrollerData.getStepSizeMillis());
if (val >= slider.getMinimum() && val <= slider.getMaximum()) {
// System.out.printf("Set slider val %d in range %d to %d\n", val, slider.getMinimum(), slider.getMaximum());
slider.setValue(val);
}
}

View File

@ -191,9 +191,9 @@ public class ViewerScrollerManager extends AbstractScrollManager implements PamS
*/
private void loadDataQueueItem(DataLoadQueData dataLoadQueData, int queuePosition, ViewLoadObserver loadObserver) {
PamDataBlock dataBlock = dataLoadQueData.getPamDataBlock();
if (dataBlock instanceof OfflineEventDataBlock) {
System.out.println(dataBlock);
}
// if (dataBlock instanceof OfflineEventDataBlock) {
// System.out.println("in loadDataQueueItem" + dataBlock);
// }
// 2019-11-12 add a check of the counts to this 'if' statement as well. If the data start time is negative
// (which can indicate that this is a 'special' data block and we should be loading all of it rather than just
@ -699,6 +699,23 @@ public class ViewerScrollerManager extends AbstractScrollManager implements PamS
if (aScroller == pamScroller) {
continue;
}
/*
* Can end up with some horrible feedback here if two
* coupled scrollers bring in rounding errors and start
* to oscillate each other.
*/
long currentVal = aScroller.getValueMillis();
long change = Math.abs(value-currentVal);
long range = aScroller.getMaximumMillis() - aScroller.getMinimumMillis();
if (range == 0) {
aScroller.setValueMillis(aScroller.getMinimumMillis());
continue;
}
double fracChange = (double) change / (double) range;
if (fracChange <= .0001) {
continue;
}
aScroller.setValueMillis(value);
}
}

View File

@ -14,6 +14,8 @@ import pamViewFX.fxNodes.PamSpinner;
*/
public class FreqBandPane extends PamGridPane {
private final static double FREQ_SPINNER_WIDTH= 130;
/**
* High pass spinner.
@ -23,7 +25,7 @@ public class FreqBandPane extends PamGridPane {
/**
* Low pass frequency spinner.
*/
private Spinner<Double> lowPassFreq;
private PamSpinner<Double> lowPassFreq;
/**
* Layout of the pane- either horizontal or vertical
@ -65,14 +67,14 @@ public class FreqBandPane extends PamGridPane {
this.setHgap(5);
this.setVgap(5);
highPassFreq=new PamSpinner<Double>(10.,500000.,1000.,2000.);
highPassFreq=new PamSpinner<Double>(0.,500000.,1000.,2000.);
highPassFreq.getStyleClass().add(Spinner.STYLE_CLASS_SPLIT_ARROWS_HORIZONTAL);
highPassFreq.getValueFactory().valueProperty().addListener((obs, before, after)->{
if (after>=lowPassFreq.getValue()) lowPassFreq.getValueFactory().setValue(Math.min(sampleRate/2.,highPassFreq.getValue()+100));
if (after>sampleRate/2.) highPassFreq.getValueFactory().setValue(sampleRate/2.);
});
// highPassFreq.getValueFactory().valueProperty().addListener((obs, before, after)->{
// if (after>=lowPassFreq.getValue()) lowPassFreq.getValueFactory().setValue(Math.min(sampleRate/2.,highPassFreq.getValue()+100));
// if (after>sampleRate/2.) highPassFreq.getValueFactory().setValue(sampleRate/2.);
// });
highPassFreq.setEditable(true);
//highPassFreq.setPrefWidth(140);
highPassFreq.setMinWidth(FREQ_SPINNER_WIDTH);
//highCut.setPrefColumnCount(6);
if (orientation==Orientation.VERTICAL){
@ -86,15 +88,15 @@ public class FreqBandPane extends PamGridPane {
this.add(highPassHzLabel=new Label("Hz"), 2, 0);
}
lowPassFreq=new PamSpinner<Double>(1.,500000.,2000.,2000.);
lowPassFreq=new PamSpinner<Double>(0.,500000.,2000.,2000.);
lowPassFreq.getStyleClass().add(Spinner.STYLE_CLASS_SPLIT_ARROWS_HORIZONTAL);
lowPassFreq.getValueFactory().valueProperty().addListener((obs, before, after)->{
if (after<=highPassFreq.getValue()) highPassFreq.getValueFactory().setValue(Math.min(0,lowPassFreq.getValue()-100));
if (after>sampleRate/2.) lowPassFreq.getValueFactory().setValue(sampleRate/2.);
});
// lowPassFreq.getValueFactory().valueProperty().addListener((obs, before, after)->{
// if (after<=highPassFreq.getValue()) highPassFreq.getValueFactory().setValue(Math.min(0,lowPassFreq.getValue()-100));
// if (after>sampleRate/2.) lowPassFreq.getValueFactory().setValue(sampleRate/2.);
//
// });
lowPassFreq.setEditable(true);
//lowPassFreq.setPrefWidth(140);
lowPassFreq.setMinWidth(FREQ_SPINNER_WIDTH);
if (orientation==Orientation.VERTICAL){

View File

@ -17,6 +17,7 @@ import pamViewFX.PamGuiManagerFX;
import pamViewFX.fxNodes.PamGridPane;
import pamViewFX.fxNodes.PamHBox;
import pamViewFX.fxNodes.PamVBox;
import pamViewFX.validator.PamValidator;
import PamUtils.PamUtils;
import PamView.GroupedSourceParameters;
import PamguardMVC.PamConstants;
@ -76,7 +77,7 @@ public class GroupedSourcePaneFX extends SourcePaneFX {
@Override
protected void createPanel() {
channelValidator = new Validator();
channelValidator = new PamValidator();
sourcePane=new PamGridPane();
sourcePane.setVgap(5);

View File

@ -0,0 +1,17 @@
package pamViewFX.validator;
import net.synedra.validatorfx.Validator;
/**
* Extension of the validator class to add PAMGuard specific functions.
* @author Jamie Macaulay
*
*/
public class PamValidator extends Validator {
public PamValidator() {
super();
// TODO Auto-generated constructor stub
}
}

View File

@ -22,6 +22,7 @@ import javafx.scene.canvas.GraphicsContext;
import javafx.scene.paint.Color;
import javafx.scene.shape.Polygon;
import rawDeepLearningClassifier.DLControl;
import rawDeepLearningClassifier.dlClassification.DLClassName;
import rawDeepLearningClassifier.dlClassification.DLDataUnit;
/**
@ -80,6 +81,16 @@ public class DLPredictionPlotInfoFX extends GenericLinePlotInfo {
frequencyInfo = new GenericScaleInfo(0, 1, ParameterType.FREQUENCY, ParameterUnits.HZ);
DLClassName[] classNames = getDlControl().getDLModel().getClassNames();
//make sure this is initialised otherwise the plot won't work when first created.
if (dlPredParams.lineInfos==null ) dlPredParams.lineInfos = new LineInfo[classNames.length];
for (int i=0; i<classNames.length; i++) {
if (dlPredParams.lineInfos[i]==null) {
dlPredParams.lineInfos[i] = new LineInfo(true, Color.rgb(0, 0, 255%(i*30 + 50)));
}
}
addScaleInfo(probabilityScaleInfo);
addScaleInfo(frequencyInfo);
}

View File

@ -36,6 +36,7 @@ import rawDeepLearningClassifier.segmenter.SegmenterProcess.GroupedRawData;
*/
public class DLClassifyProcess extends PamInstantProcess {
/**
* Holds all model results but no other information
*/
@ -538,7 +539,9 @@ public class DLClassifyProcess extends PamInstantProcess {
@Override
public void pamStop() {
runModel(); //make sure to run the last data in the buffer.
this.dlControl.getDLModel().closeModel();
//21/11/2022 - it seems like this causes a memory leak when models are reopened and closed every file...
//this.dlControl.getDLModel().closeModel();
}
/**

View File

@ -168,7 +168,11 @@ public class GenericDLClassifier implements DLClassiferModel, PamSettings {
@Override
public void closeModel() {
// TODO Auto-generated method stub
//very important to prevent memory leak for long term processing.
if (genericModelWorker.getModel()!=null && genericModelWorker.getModel().getModel()!=null) {
//System.out.println("CLOSE GENERNIC MODEL");
genericModelWorker.getModel().getModel().close();
}
}

View File

@ -284,6 +284,8 @@ public class GenericModelParser {
}
paramsClone.numClasses = classNames.length;
if (classNameManager!=null) {
paramsClone.classNames = classNameManager.makeClassNames(classNames);

View File

@ -1,5 +1,7 @@
package rawDeepLearningClassifier.dlClassification.genericModel;
import java.nio.file.Paths;
import org.apache.commons.io.FilenameUtils;
import org.jamdev.jdl4pam.genericmodel.GenericModel;
import org.jamdev.jdl4pam.transforms.DLTransform;
@ -67,10 +69,24 @@ public class GenericModelWorker extends DLModelWorker<GenericPrediction> {
// if (DLControl.PLUGIN_BUILD) {
// PluginClassloader newCL = PamModel.getPamModel().getClassLoader();
// Thread.currentThread().setContextClassLoader(newCL);
// }
// if (genericModel!=null) {
// System.out.println(Paths.get(genericModel.getModel().getName()));
// System.out.println(Paths.get(genericParams.modelPath));
// System.out.println(Paths.get(genericModel.getModel().getName()).equals(Paths.get(genericParams.modelPath)));
// }
//first open the model and get the correct parameters.
genericModel = new PamGenericModel(genericParams.modelPath);
//21/11/2022 - Added a null and filename check here to stop the mdoel reloading everytime PAMGuard hits a new file or
//is stopped or started - this was causing a memory leak.
if (genericModel==null || !Paths.get(genericModel.getModel().getName()).equals(Paths.get(genericParams.modelPath))) {
//System.out.println(Paths.get(genericParams.modelPath));
genericModel = new PamGenericModel(genericParams.modelPath);
//System.out.println("LOAD A NEW MODEL: ");
//System.out.println(genericModel.getModel().getModelPath().getFileName());
}
//is this a waveform or a spectrogram model?
DLTransform transform = genericParams.dlTransfroms.get(genericParams.dlTransfroms.size()-1);

View File

@ -65,6 +65,8 @@ public class PamGenericModel {
public PamGenericModel(String modelPath) throws MalformedModelException, IOException{
//System.out.println("NEW GENERIC MODEL:");
File file = new File(modelPath);
//String modelPath = "/Users/au671271/Google Drive/Aarhus_research/PAMGuard_bats_2020/deep_learning/BAT/models/bats_denmark/BAT_4ms_256ft_8hop_128_NOISEAUG_40000_100000_-100_0_256000_JAMIE.pk";
@ -95,7 +97,6 @@ public class PamGenericModel {
if (model == null) {
System.err.println("Generic Model: Could not load model: " + modelPath);
}
else {
if (model!=null && model.describeInput()!=null) {
System.out.println("Generic Model: Input: " + model.describeInput().toString());
@ -117,7 +118,6 @@ public class PamGenericModel {
//predictor for the model if using
wavePredictor = model.newPredictor(waveTranslator);
}
}
@ -201,8 +201,6 @@ public class PamGenericModel {
}
public Model getModel() {
return model;
}

View File

@ -1,6 +1,7 @@
package rawDeepLearningClassifier.dlClassification.ketos;
import java.io.File;
import java.nio.file.Paths;
import java.util.ArrayList;
import org.jamdev.jdl4pam.ketos.KetosModel;
@ -15,6 +16,7 @@ import PamModel.PamModel.PluginClassloader;
import rawDeepLearningClassifier.DLControl;
import rawDeepLearningClassifier.dlClassification.animalSpot.StandardModelParams;
import rawDeepLearningClassifier.dlClassification.genericModel.DLModelWorker;
import rawDeepLearningClassifier.dlClassification.genericModel.PamGenericModel;
/**
*
@ -32,6 +34,11 @@ public class KetosWorker extends DLModelWorker<KetosResult> {
*/
private KetosModel ketosModel;
/**
* Thelast loaded model path.,
*/
private String currentPath;
/**
* SoundSpotWorker constructor.
@ -56,7 +63,15 @@ public class KetosWorker extends DLModelWorker<KetosResult> {
Thread.currentThread().setContextClassLoader(newCL);
}
//first open the model and get the correct parameters.
ketosModel = new KetosModel(new File(ketosDLParams.modelPath));
//21/11/2022 - Added a null and filename check here to stop the mdoel reloading everytime PAMGuard hits a new file or
//is stopped or started - this was causing a memory leak.
if (ketosModel==null || currentPath ==null || !Paths.get(currentPath).equals(Paths.get(ketosDLParams.modelPath))) {
//System.out.println(Paths.get(genericParams.modelPath));
this.currentPath = ketosDLParams.modelPath;
ketosModel = new KetosModel(new File(ketosDLParams.modelPath));
//System.out.println("LOAD A NEW MODEL: ");
//System.out.println(genericModel.getModel().getModelPath().getFileName());
}
}
catch (Exception e) {
e.printStackTrace();

View File

@ -91,7 +91,8 @@ public class DataTransformPaneFactory {
case SPECTROGRAM:
settingsPane = new FFTTransformPane((SimpleTransform) dlTransfrom, new String[]{"FFT Length ", "FFT Hop"}, new String[]{"", ""});
// ((SimpleTransformPane) settingsPane).setSpinnerMinMaxValues(0, 4, Integer.MAX_VALUE, 4);
((SimpleTransformPane) settingsPane).setSpinnerMinMaxValues(1, 4, Integer.MAX_VALUE, 4);
((FFTTransformPane) settingsPane).setSpinnerMinMaxValues(1, 4, Integer.MAX_VALUE, 4);
// //make an FFT spinner here with doubling FFT lengths - DOES NOT WORK FOR SOME REASON...
// ((SimpleTransformPane) settingsPane).getSpinners().get(0).setValueFactory(new SpinnerValueFactory.ListSpinnerValueFactory<>(createStepList()));
// ((SimpleTransformPane) settingsPane).getSpinners().get(0).getValueFactory().setValue(4);

View File

@ -89,7 +89,7 @@ public class SimpleTransformPane extends DLTransformPane {
int row = 0;
int column = 0;
if (simpleTransfrom.getParams()!=null) {
// if (simpleTransfrom.getParams()!=null) {
for (int i=0; i<paramNames.length; i++) {
if (i%nParamCol == 0 && i!=0) {
row++;
@ -117,8 +117,7 @@ public class SimpleTransformPane extends DLTransformPane {
//System.out.println("New line: " + i + " " + nParamCol + " " + i%nParamCol);
}
}
// }
TitledPane titledPane = new TitledPane(simpleTransfrom.getDLTransformType().toString(), gridPane);
@ -190,8 +189,8 @@ public class SimpleTransformPane extends DLTransformPane {
SimpleTransform simpleTransform = (SimpleTransform) currParams;
//Set the new numbers
Number[] params = new Number[simpleTransform.getParams().length];
for (int i=0; i<simpleTransform.getParams().length; i++) {
Number[] params = new Number[spinners.size()];
for (int i=0; i<spinners.size(); i++) {
params[i] = spinners.get(i).getValue();
}
@ -208,6 +207,11 @@ public class SimpleTransformPane extends DLTransformPane {
SimpleTransform simpleTransform = (SimpleTransform) input;
if (simpleTransform.getParams()==null) {
System.err.println("SimpleTransformPane: params for " + simpleTransform.getDLTransformType() + " are null - maybe backwards compatibility issue ");
simpleTransform.setParams(((SimpleTransform)DLTransformsFactory.makeDLTransform(simpleTransform.getDLTransformType(), 1000)).getParams());
}
//System.out.println("Transform type: " + simpleTransform.getDLTransformType() + " " + simpleTransform.getParams().length + " " + spinners.size());
for (int i=0; i<spinners.size(); i++) {

View File

@ -451,7 +451,7 @@ public class RoccaSpecPopUp extends javax.swing.JPanel {
for(int currentFreqBin = 0; currentFreqBin < fftVals.length(); currentFreqBin++) {
rawAmp = fftVals.magsq(currentFreqBin);
dB = daq.fftAmplitude2dB(rawAmp,
channelMap,
PamUtils.getLowestChannel(channelMap),
fftData.getSampleRate(),
fftLength,
true,

View File

@ -131,7 +131,12 @@ public class GridMovement extends MovementModel implements PamSettings {
@Override
public String getUnitName() {
return getSimObject().name;
if (getSimObject() != null && getSimObject().name != null) {
return getSimObject().name;
}
else {
return "Unknown";
}
}
@Override

View File

@ -0,0 +1,23 @@
package simulatedAcquisition.sounds;
public class RandomMystecete extends RandomQuadratics {
public RandomMystecete() {
super();
double slope[] = {-150, 150};
double length[] = {.4, 1};
double meanF[] = {200, 800};
double meanCurve[] = {-300, 300};
setCurveR(meanCurve);
setLengthR(length);
setMeanR(meanF);
setSlopeR(slope);
}
@Override
public String getName() {
return "Random baleen whale (humpbackish)";
}
}

View File

@ -35,6 +35,7 @@ public class SimSignals {
simSignalList.add(new RandomWhistles());
simSignalList.add(new BranchedChirp(5000, 12000, 8000, 3000, .6));
simSignalList.add(new RightWhales());
simSignalList.add(new RandomMystecete());
simSignalList.add(new BlueWhaleD());
simSignalList.add(new WhiteNoise());
simSignalList.add(new PinkNoise());

View File

@ -24,7 +24,11 @@ import Stats.LinFit;
* a track as close as possible to the x axis.
* @author Doug Gillespie
*
* Deprecated. Not used and will probably fall over with system whereby sub detection info
* is present, but not all sub detections are.
*
*/
@Deprecated
@SuppressWarnings("rawtypes")
public class EventRotator extends AbstractTargetMotionInformation{

View File

@ -1,9 +1,13 @@
package targetMotionOld;
import pamMaths.PamVector;
import java.util.List;
import PamDetection.AbstractLocalisation;
import PamUtils.LatLong;
import PamguardMVC.PamDataUnit;
import PamguardMVC.superdet.SubdetectionInfo;
import PamguardMVC.superdet.SuperDetection;
import Stats.LinFit;
@ -74,12 +78,18 @@ public class EventRotator {
private double[] rotatedArrayAngles;
private int referenceHydrophones;
/**
* List of present (actual sub detection is not null) sub detections.
*/
private List<SubdetectionInfo<PamDataUnit>> subDetections;
/**
* @param pamDetection
*/
public EventRotator(SuperDetection pamDetection) {
super();
this.pamDetection = pamDetection;
this.subDetections = pamDetection.getPresentSubDetections();
rotatedWorldVectors = null;
calculateMetrePoints();
}
@ -90,14 +100,14 @@ public class EventRotator {
*/
private void calculateMetrePoints() {
lastUpdateTime = pamDetection.getLastUpdateTime();
nSubDetections = pamDetection.getSubDetectionsCount();
nSubDetections = subDetections.size();
subDetectionOrigins = new PamVector[nSubDetections];
subDetectionHeadings = new PamVector[nSubDetections];
pointTimes = new long[nSubDetections];
if (nSubDetections == 0) {
return;
}
PamDataUnit pd = pamDetection.getSubDetection(0);
PamDataUnit pd = subDetections.get(0).getSubDetection();
if (pd == null) {
return;
}
@ -110,7 +120,10 @@ public class EventRotator {
LatLong detOrigin;
for (int i = 0; i < nSubDetections; i++) {
pd = pamDetection.getSubDetection(i);
pd = subDetections.get(i).getSubDetection();
if (pd == null) {
continue;
}
localisation = pd.getLocalisation();
if (localisation == null) {
continue;
@ -152,6 +165,9 @@ public class EventRotator {
rotatedOrigins = new PamVector[nSubDetections];
rotatedHeadings = new PamVector[nSubDetections];
for (int i = 0; i < nSubDetections; i++) {
if (subDetectionOrigins[i] == null) {
continue;
}
subDetectionHeadings[i] = new PamVector(Math.cos(Math.PI/2-rotatedArrayAngles[i]), Math.sin(Math.PI/2-rotatedArrayAngles[i]), 0);
rotatedOrigins[i] = subDetectionOrigins[i].rotate(-referenceAngle);
rotatedArrayAngles[i] = Math.PI/2. - rotatedArrayAngles[i];
@ -170,7 +186,7 @@ public class EventRotator {
PamDataUnit pd;
AbstractLocalisation localisation;
for (int i = 0; i < nSubDetections; i++) {
pd = pamDetection.getSubDetection(i);
pd = subDetections.get(i).getSubDetection();
localisation = pd.getLocalisation();
if (localisation == null) {
continue;
@ -187,7 +203,7 @@ public class EventRotator {
PamDataUnit pd;
AbstractLocalisation localisation;
for (int i = 0; i < nSubDetections; i++) {
pd = pamDetection.getSubDetection(i);
pd = subDetections.get(i).getSubDetection();
localisation = pd.getLocalisation();
if (localisation == null) {
continue;

View File

@ -4,6 +4,7 @@ import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.util.ArrayList;
import java.util.List;
import javax.swing.JPanel;
@ -18,6 +19,7 @@ import PamUtils.LatLong;
import PamguardMVC.PamDataBlock;
import PamguardMVC.PamDataUnit;
import PamguardMVC.dataSelector.DataSelector;
import PamguardMVC.superdet.SubdetectionInfo;
import clickDetector.ClickDataBlock;
import targetMotionOld.TargetMotionLocaliser;
@ -66,9 +68,14 @@ public class DialogMap3DSwing<T extends GroupDetection> extends DialogMap<T> {
mapDetData.allAvailable = true;
mapDetData.select = true;
int nSub = currentEvent.getSubDetectionsCount();
List<SubdetectionInfo<PamDataUnit>> subDets = currentEvent.getPresentSubDetections();
int nSub = subDets.size();
for (int i = 0; i < nSub; i++) {
PamDataUnit subDet = currentEvent.getSubDetection(i);
PamDataUnit subDet = subDets.get(i).getSubDetection();
if (subDet == null) {
continue;
}
MapDetectionData subDetData = mapDetectionsManager.findDetectionData(subDet.getParentDataBlock());
if (subDetData != null && subDetData != mapDetData) {
mapDetData = subDetData;
@ -81,8 +88,8 @@ public class DialogMap3DSwing<T extends GroupDetection> extends DialogMap<T> {
*/
LatLong eventCentre = currentEvent.getOriginLatLong(true);
if (nSub >= 2) {
LatLong ll1 = currentEvent.getSubDetection(0).getOriginLatLong(true);
LatLong ll2 = currentEvent.getSubDetection(nSub-1).getOriginLatLong(true);
LatLong ll1 = subDets.get(0).getSubDetection().getOriginLatLong(true);
LatLong ll2 = subDets.get(nSub-1).getSubDetection().getOriginLatLong(true);
if (ll1 != null & ll2 != null) {
double lat = (ll1.getLatitude() + ll2.getLatitude())/2.;
double lon = (ll1.getLongitude() + ll2.getLongitude())/2.;