mirror of
https://github.com/PAMGuard/PAMGuard.git
synced 2025-02-16 17:22:46 +00:00
Implementing FPOD and updates to deep leanring module
This commit is contained in:
parent
cf93b11a10
commit
9957bd3fa3
@ -6,8 +6,7 @@
|
||||
<attribute name="maven.pomderived" value="true"/>
|
||||
</attributes>
|
||||
</classpathentry>
|
||||
<classpathentry kind="src" path="test"/>
|
||||
<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/JavaSE-11">
|
||||
<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/JavaSE-17">
|
||||
<attributes>
|
||||
<attribute name="maven.pomderived" value="true"/>
|
||||
</attributes>
|
||||
|
@ -1,9 +1,9 @@
|
||||
eclipse.preferences.version=1
|
||||
org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode=enabled
|
||||
org.eclipse.jdt.core.compiler.codegen.methodParameters=do not generate
|
||||
org.eclipse.jdt.core.compiler.codegen.targetPlatform=11
|
||||
org.eclipse.jdt.core.compiler.codegen.targetPlatform=17
|
||||
org.eclipse.jdt.core.compiler.codegen.unusedLocal=preserve
|
||||
org.eclipse.jdt.core.compiler.compliance=11
|
||||
org.eclipse.jdt.core.compiler.compliance=17
|
||||
org.eclipse.jdt.core.compiler.debug.lineNumber=generate
|
||||
org.eclipse.jdt.core.compiler.debug.localVariable=generate
|
||||
org.eclipse.jdt.core.compiler.debug.sourceFile=generate
|
||||
@ -13,4 +13,4 @@ org.eclipse.jdt.core.compiler.problem.enumIdentifier=error
|
||||
org.eclipse.jdt.core.compiler.problem.forbiddenReference=warning
|
||||
org.eclipse.jdt.core.compiler.problem.reportPreviewFeatures=warning
|
||||
org.eclipse.jdt.core.compiler.release=enabled
|
||||
org.eclipse.jdt.core.compiler.source=11
|
||||
org.eclipse.jdt.core.compiler.source=17
|
||||
|
@ -4,7 +4,7 @@
|
||||
<groupId>org.pamguard</groupId>
|
||||
<artifactId>Pamguard</artifactId>
|
||||
<name>Pamguard Java12+</name>
|
||||
<version>2.02.09c</version>
|
||||
<version>2.02.09d</version>
|
||||
<description>Pamguard for Java 12+, using Maven to control dependcies</description>
|
||||
<url>www.pamguard.org</url>
|
||||
<organization>
|
||||
@ -12,7 +12,7 @@
|
||||
<url>http://www.smru.st-andrews.ac.uk</url>
|
||||
</organization>
|
||||
<build>
|
||||
<sourceDirectory>src</sourceDirectory>
|
||||
<sourceDirectory>${basedir}/src</sourceDirectory>
|
||||
<resources>
|
||||
<resource>
|
||||
<directory>src</directory>
|
||||
@ -53,7 +53,7 @@
|
||||
<plugins>
|
||||
<plugin>
|
||||
<artifactId>maven-compiler-plugin</artifactId>
|
||||
<version>3.8.1</version>
|
||||
<version>3.12.1</version>
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>org.eclipse.tycho</groupId>
|
||||
@ -62,22 +62,14 @@
|
||||
</dependency>
|
||||
</dependencies>
|
||||
<configuration>
|
||||
<release>11</release>
|
||||
<release>17</release>
|
||||
<compilerId>jdt</compilerId>
|
||||
<compilerArguments>
|
||||
<properties>.settings/org.eclipse.jdt.core.prefs</properties>
|
||||
</compilerArguments>
|
||||
</configuration>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.openjfx</groupId>
|
||||
<artifactId>javafx-maven-plugin</artifactId>
|
||||
<version>0.0.6</version>
|
||||
<configuration>
|
||||
<source>17</source>
|
||||
<target>17</target>
|
||||
<release>17</release>
|
||||
</configuration>
|
||||
<version>0.0.8</version>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<artifactId>maven-shade-plugin</artifactId>
|
||||
|
434
pom.xml
434
pom.xml
@ -5,8 +5,8 @@
|
||||
<groupId>org.pamguard</groupId>
|
||||
<artifactId>Pamguard</artifactId>
|
||||
<version>2.02.09d</version>
|
||||
<name>Pamguard Java12+</name>
|
||||
<description>Pamguard for Java 12+, using Maven to control dependcies</description>
|
||||
<name>Pamguard</name>
|
||||
<description>Pamguard using Maven to control dependencies</description>
|
||||
<url>www.pamguard.org</url>
|
||||
<organization>
|
||||
<name>Sea Mammal Research Unit, University of St. Andrews</name>
|
||||
@ -14,225 +14,219 @@
|
||||
</organization>
|
||||
|
||||
|
||||
<properties>
|
||||
<javafx.version>16</javafx.version>
|
||||
<maven.compiler.source>11</maven.compiler.source>
|
||||
<maven.compiler.target>11</maven.compiler.target>
|
||||
</properties>
|
||||
<properties>
|
||||
<project.build.sourceEncoding>ISO-8859-1</project.build.sourceEncoding>
|
||||
<javafx.version>17</javafx.version>
|
||||
<maven.compiler.source>11</maven.compiler.source>
|
||||
<maven.compiler.target>11</maven.compiler.target>
|
||||
</properties>
|
||||
|
||||
<build>
|
||||
<sourceDirectory>src</sourceDirectory>
|
||||
<resources>
|
||||
<resource>
|
||||
<directory>src</directory>
|
||||
<excludes>
|
||||
<exclude>**/*.java</exclude> <!-- don't include any source files -->
|
||||
<exclude>jars/*.*</exclude> <!-- don't include files in the jars folder -->
|
||||
</excludes>
|
||||
</resource>
|
||||
</resources>
|
||||
<plugins>
|
||||
<plugin>
|
||||
|
||||
<!-- original maven compiler definition - uses the JRE's javac compiler, not the one Eclipse uses
|
||||
<artifactId>maven-compiler-plugin</artifactId>
|
||||
<version>3.8.0</version>
|
||||
<configuration>
|
||||
<release>13</release>
|
||||
</configuration>
|
||||
-->
|
||||
|
||||
<!-- attempt to use the Eclipse JDT compiler, so that the errors match when building
|
||||
https://stackoverflow.com/questions/38070326/java-generics-compiler-error-not-shown-in-eclipse
|
||||
https://wiki.eclipse.org/JDT/FAQ#Can_I_use_JDT_outside_Eclipse_to_compile_Java_code.3F
|
||||
https://wiki.eclipse.org/Tycho/FAQ#Can_I_use_the_Tycho_compiler_support_in_non-OSGi_projects.2C_too.3F
|
||||
-->
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-compiler-plugin</artifactId>
|
||||
<version>3.8.1</version>
|
||||
<configuration>
|
||||
|
||||
<!-- set compiler to use Java version 11 API https://docs.oracle.com/javase/9/tools/javac.htm#JSWOR627 -->
|
||||
<release>11</release>
|
||||
<compilerId>jdt</compilerId>
|
||||
<compilerArguments>
|
||||
<properties>.settings/org.eclipse.jdt.core.prefs</properties> <!-- make sure to use same params as what Eclipse uses -->
|
||||
</compilerArguments>
|
||||
</configuration>
|
||||
|
||||
<dependencies>
|
||||
<!-- https://mvnrepository.com/artifact/org.eclipse.tycho/tycho-compiler-jdt -->
|
||||
<dependency>
|
||||
<groupId>org.eclipse.tycho</groupId>
|
||||
<artifactId>tycho-compiler-jdt</artifactId>
|
||||
<version>1.5.1</version>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
</plugin>
|
||||
|
||||
<plugin>
|
||||
<groupId>org.openjfx</groupId>
|
||||
<artifactId>javafx-maven-plugin</artifactId>
|
||||
<version>0.0.6</version>
|
||||
<configuration>
|
||||
<source>17</source>
|
||||
<target>17</target>
|
||||
<release>17</release>
|
||||
</configuration>
|
||||
</plugin>
|
||||
<build>
|
||||
|
||||
<!-- Maven Shade plugin - for creating the uberjar / fatjar -->
|
||||
<!-- see http://maven.apache.org/plugins/maven-shade-plugin/index.html for details -->
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-shade-plugin</artifactId>
|
||||
<version>3.2.1</version>
|
||||
<configuration>
|
||||
<transformers>
|
||||
<transformer
|
||||
implementation="org.apache.maven.plugins.shade.resource.ServicesResourceTransformer" />
|
||||
</transformers>
|
||||
</configuration>
|
||||
<executions>
|
||||
<execution>
|
||||
<phase>package</phase>
|
||||
<goals>
|
||||
<goal>shade</goal>
|
||||
</goals>
|
||||
<configuration>
|
||||
<transformers>
|
||||
<transformer implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer">
|
||||
<manifestEntries>
|
||||
<Main-Class>pamguard.Pamguard</Main-Class>
|
||||
<Class-Path>.</Class-Path> <!-- this is from the orig ant build file -->
|
||||
<SplashScreen-Image>Resources/pgBlankSplash.png</SplashScreen-Image> <!-- this is from the orig ant build file -->
|
||||
</manifestEntries>
|
||||
</transformer>
|
||||
<transformer implementation="org.apache.maven.plugins.shade.resource.ServicesResourceTransformer" />
|
||||
</transformers>
|
||||
<filters>
|
||||
<filter>
|
||||
<artifact>*:*</artifact>
|
||||
<excludes>
|
||||
<exclude>META-INF/*.SF</exclude> <!-- get rid of manifests from library jars - also done in orig ant build file -->
|
||||
<exclude>META-INF/*.DSA</exclude>
|
||||
<exclude>META-INF/*.RSA</exclude>
|
||||
</excludes>
|
||||
</filter>
|
||||
</filters>
|
||||
</configuration>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
|
||||
<!-- The Maven-JDEPS plugin, to analyze necessary JDK dependencies. See
|
||||
this site for details: https://maven.apache.org/plugins/maven-jdeps-plugin/index.html -->
|
||||
<plugin>
|
||||
<groupId>com.github.marschall</groupId>
|
||||
<artifactId>jdeps-maven-plugin</artifactId>
|
||||
<version>0.5.1</version>
|
||||
</plugin>
|
||||
|
||||
<!-- The Maven dependency plugin, which can copy all dependencies into a temp folder for jdeps analysis -->
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-dependency-plugin</artifactId>
|
||||
<version>3.1.1</version>
|
||||
<executions>
|
||||
<execution>
|
||||
<id>copy-dependencies</id>
|
||||
<phase>package</phase>
|
||||
<goals>
|
||||
<goal>copy-dependencies</goal>
|
||||
</goals>
|
||||
<configuration>
|
||||
<outputDirectory>${project.build.directory}/tempDependencies</outputDirectory>
|
||||
<overWriteReleases>false</overWriteReleases>
|
||||
<overWriteSnapshots>false</overWriteSnapshots>
|
||||
<overWriteIfNewer>true</overWriteIfNewer>
|
||||
</configuration>
|
||||
</execution>
|
||||
|
||||
<!-- this deletes all the dependencies in the local repository and downloads them again.
|
||||
Run a Maven > Update after doing this in order to properly reset the dependencies. Also, you
|
||||
will need to add the 3 jar files (x3, JasioHost and jave) back into the local repository after
|
||||
running this command -->
|
||||
|
||||
<!-- I'm not sure why, but every time I try to run the shade:shade build to create a
|
||||
fatjar it first runs this, which deletes all of the dependencies and completely fails.
|
||||
I think it has something to do with the lifecycle mapping, but that's beyond my Maven
|
||||
abilities right now.
|
||||
I can't even remember why I added this in the first place, so I'm going to comment
|
||||
it out
|
||||
<execution>
|
||||
<id>purge-local-dependencies</id>
|
||||
<phase>process-sources</phase>
|
||||
<goals>
|
||||
<goal>purge-local-repository</goal>
|
||||
</goals>
|
||||
<configuration>
|
||||
</configuration>
|
||||
</execution>
|
||||
-->
|
||||
</executions>
|
||||
</plugin>
|
||||
|
||||
<!-- Define where the source and test directories are -->
|
||||
<sourceDirectory>${basedir}/src</sourceDirectory>
|
||||
<testSourceDirectory>${basedir}/src/test</testSourceDirectory> <!-- where the Unit tets are located -->
|
||||
<resources>
|
||||
<resource>
|
||||
<directory>src</directory>
|
||||
<excludes>
|
||||
<exclude>**/*.java</exclude> <!-- don't include any source files -->
|
||||
<exclude>jars/*.*</exclude> <!-- don't include files in the jars folder -->
|
||||
</excludes>
|
||||
</resource>
|
||||
</resources>
|
||||
|
||||
|
||||
<plugins>
|
||||
<!-- original maven compiler definition - uses the JRE's javac compiler, not the one Eclipse uses
|
||||
<artifactId>maven-compiler-plugin</artifactId>
|
||||
<version>3.8.0</version>
|
||||
<configuration>
|
||||
<release>13</release>
|
||||
</configuration>
|
||||
-->
|
||||
|
||||
<!-- attempt to use the Eclipse JDT compiler, so that the errors match when building
|
||||
https://stackoverflow.com/questions/38070326/java-generics-compiler-error-not-shown-in-eclipse
|
||||
https://wiki.eclipse.org/JDT/FAQ#Can_I_use_JDT_outside_Eclipse_to_compile_Java_code.3F
|
||||
https://wiki.eclipse.org/Tycho/FAQ#Can_I_use_the_Tycho_compiler_support_in_non-OSGi_projects.2C_too.3F
|
||||
-->
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-compiler-plugin</artifactId>
|
||||
<version>3.12.1</version>
|
||||
<configuration>
|
||||
<!-- set compiler to use Java version 11 API https://docs.oracle.com/javase/9/tools/javac.htm#JSWOR627 -->
|
||||
<release>17</release>
|
||||
<compilerId>jdt</compilerId>
|
||||
</configuration>
|
||||
<dependencies>
|
||||
<!-- https://mvnrepository.com/artifact/org.eclipse.tycho/tycho-compiler-jdt -->
|
||||
<dependency>
|
||||
<groupId>org.eclipse.tycho</groupId>
|
||||
<artifactId>tycho-compiler-jdt</artifactId>
|
||||
<version>1.5.1</version>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
</plugin>
|
||||
|
||||
<!-- Set up javafx properly. -->
|
||||
<plugin>
|
||||
<groupId>org.openjfx</groupId>
|
||||
<artifactId>javafx-maven-plugin</artifactId>
|
||||
<version>0.0.8</version>
|
||||
</plugin>
|
||||
|
||||
<!-- Maven Shade plugin - for creating the uberjar / fatjar -->
|
||||
<!-- see http://maven.apache.org/plugins/maven-shade-plugin/index.html for details -->
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-shade-plugin</artifactId>
|
||||
<version>3.2.1</version>
|
||||
<configuration>
|
||||
<transformers>
|
||||
<transformer
|
||||
implementation="org.apache.maven.plugins.shade.resource.ServicesResourceTransformer" />
|
||||
</transformers>
|
||||
</configuration>
|
||||
<executions>
|
||||
<execution>
|
||||
<phase>package</phase>
|
||||
<goals>
|
||||
<goal>shade</goal>
|
||||
</goals>
|
||||
<configuration>
|
||||
<transformers>
|
||||
<transformer implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer">
|
||||
<manifestEntries>
|
||||
<Main-Class>pamguard.Pamguard</Main-Class>
|
||||
<Class-Path>.</Class-Path> <!-- this is from the orig ant build file -->
|
||||
<SplashScreen-Image>Resources/pgBlankSplash.png</SplashScreen-Image> <!-- this is from the orig ant build file -->
|
||||
</manifestEntries>
|
||||
</transformer>
|
||||
<transformer implementation="org.apache.maven.plugins.shade.resource.ServicesResourceTransformer" />
|
||||
</transformers>
|
||||
<filters>
|
||||
<filter>
|
||||
<artifact>*:*</artifact>
|
||||
<excludes>
|
||||
<exclude>META-INF/*.SF</exclude> <!-- get rid of manifests from library jars - also done in orig ant build file -->
|
||||
<exclude>META-INF/*.DSA</exclude>
|
||||
<exclude>META-INF/*.RSA</exclude>
|
||||
</excludes>
|
||||
</filter>
|
||||
</filters>
|
||||
</configuration>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
|
||||
<!-- The Maven-JDEPS plugin, to analyze necessary JDK dependencies. See
|
||||
this site for details: https://maven.apache.org/plugins/maven-jdeps-plugin/index.html -->
|
||||
<plugin>
|
||||
<groupId>com.github.marschall</groupId>
|
||||
<artifactId>jdeps-maven-plugin</artifactId>
|
||||
<version>0.5.1</version>
|
||||
</plugin>
|
||||
|
||||
<!-- The Maven dependency plugin, which can copy all dependencies into a temp folder for jdeps analysis -->
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-dependency-plugin</artifactId>
|
||||
<version>3.1.1</version>
|
||||
<executions>
|
||||
<execution>
|
||||
<id>copy-dependencies</id>
|
||||
<phase>package</phase>
|
||||
<goals>
|
||||
<goal>copy-dependencies</goal>
|
||||
</goals>
|
||||
<configuration>
|
||||
<outputDirectory>${project.build.directory}/tempDependencies</outputDirectory>
|
||||
<overWriteReleases>false</overWriteReleases>
|
||||
<overWriteSnapshots>false</overWriteSnapshots>
|
||||
<overWriteIfNewer>true</overWriteIfNewer>
|
||||
</configuration>
|
||||
</execution>
|
||||
<!-- this deletes all the dependencies in the local repository and downloads them again.
|
||||
Run a Maven > Update after doing this in order to properly reset the dependencies. Also, you
|
||||
will need to add the 3 jar files (x3, JasioHost and jave) back into the local repository after
|
||||
running this command -->
|
||||
|
||||
<!-- I'm not sure why, but every time I try to run the shade:shade build to create a
|
||||
fatjar it first runs this, which deletes all of the dependencies and completely fails.
|
||||
I think it has something to do with the lifecycle mapping, but that's beyond my Maven
|
||||
abilities right now.
|
||||
I can't even remember why I added this in the first place, so I'm going to comment
|
||||
it out
|
||||
<execution>
|
||||
<id>purge-local-dependencies</id>
|
||||
<phase>process-sources</phase>
|
||||
<goals>
|
||||
<goal>purge-local-repository</goal>
|
||||
</goals>
|
||||
<configuration>
|
||||
</configuration>
|
||||
</execution>
|
||||
-->
|
||||
</executions>
|
||||
</plugin>
|
||||
|
||||
</plugins>
|
||||
|
||||
|
||||
<pluginManagement>
|
||||
<plugins>
|
||||
<!--This plugin's configuration is used to store Eclipse m2e settings only. It has no influence on the Maven build itself.-->
|
||||
<plugin>
|
||||
<groupId>org.eclipse.m2e</groupId>
|
||||
<artifactId>lifecycle-mapping</artifactId>
|
||||
<version>1.0.0</version>
|
||||
<configuration>
|
||||
<lifecycleMappingMetadata>
|
||||
<pluginExecutions>
|
||||
<pluginExecution>
|
||||
<pluginExecutionFilter>
|
||||
<groupId>
|
||||
org.apache.maven.plugins
|
||||
</groupId>
|
||||
<artifactId>
|
||||
maven-dependency-plugin
|
||||
</artifactId>
|
||||
<versionRange>
|
||||
[3.1.1,)
|
||||
</versionRange>
|
||||
<goals>
|
||||
<goal>
|
||||
purge-local-repository
|
||||
</goal>
|
||||
</goals>
|
||||
</pluginExecutionFilter>
|
||||
<action>
|
||||
<ignore></ignore>
|
||||
</action>
|
||||
</pluginExecution>
|
||||
</pluginExecutions>
|
||||
</lifecycleMappingMetadata>
|
||||
</configuration>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</pluginManagement>
|
||||
</build>
|
||||
|
||||
</plugins>
|
||||
<pluginManagement>
|
||||
<plugins>
|
||||
<!--This plugin's configuration is used to store Eclipse m2e settings only. It has no influence on the Maven build itself.-->
|
||||
<plugin>
|
||||
<groupId>org.eclipse.m2e</groupId>
|
||||
<artifactId>lifecycle-mapping</artifactId>
|
||||
<version>1.0.0</version>
|
||||
<configuration>
|
||||
<lifecycleMappingMetadata>
|
||||
<pluginExecutions>
|
||||
<pluginExecution>
|
||||
<pluginExecutionFilter>
|
||||
<groupId>
|
||||
org.apache.maven.plugins
|
||||
</groupId>
|
||||
<artifactId>
|
||||
maven-dependency-plugin
|
||||
</artifactId>
|
||||
<versionRange>
|
||||
[3.1.1,)
|
||||
</versionRange>
|
||||
<goals>
|
||||
<goal>
|
||||
purge-local-repository
|
||||
</goal>
|
||||
</goals>
|
||||
</pluginExecutionFilter>
|
||||
<action>
|
||||
<ignore></ignore>
|
||||
</action>
|
||||
</pluginExecution>
|
||||
</pluginExecutions>
|
||||
</lifecycleMappingMetadata>
|
||||
</configuration>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</pluginManagement>
|
||||
</build>
|
||||
|
||||
<reporting>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>com.github.marschall</groupId>
|
||||
<artifactId>jdeps-maven-plugin</artifactId>
|
||||
<version>0.5.1</version>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</reporting>
|
||||
<reporting>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>com.github.marschall</groupId>
|
||||
<artifactId>jdeps-maven-plugin</artifactId>
|
||||
<version>0.5.1</version>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</reporting>
|
||||
|
||||
|
||||
<!-- ************************* Extra Repositories ************************************* -->
|
||||
<repositories>
|
||||
|
||||
<repositories>
|
||||
<!-- Project repo to hold the custom jar files that are not available in Maven. Do
|
||||
this so that we don't have to do the extra step of manually installing jar files in the local repo -->
|
||||
<repository>
|
||||
@ -308,12 +302,12 @@
|
||||
<url>https://repo1.maven.org/maven2</url>
|
||||
</repository>
|
||||
|
||||
</repositories>
|
||||
</repositories>
|
||||
|
||||
|
||||
<!-- ************************* Dependencies ************************************* -->
|
||||
<dependencies>
|
||||
|
||||
|
||||
<!--jpam project - utilities -->
|
||||
<dependency>
|
||||
<groupId>io.github.macster110</groupId>
|
||||
@ -836,12 +830,6 @@ C:\Users\*yourusername*\.m2\repository\pamguard\org\x3\2.2.2-->
|
||||
<version>1.6.5-1</version>
|
||||
</dependency>
|
||||
|
||||
<!-- Theme for JavaFX -->
|
||||
<dependency>
|
||||
<groupId>io.github.mkpaz</groupId>
|
||||
<artifactId>atlantafx-base</artifactId>
|
||||
<version>1.0.0</version>
|
||||
</dependency>
|
||||
|
||||
<!-- Extra 3D bits for JavaFX -->
|
||||
<dependency>
|
||||
|
@ -14,6 +14,7 @@ import javafx.event.EventHandler;
|
||||
import javafx.scene.AmbientLight;
|
||||
import javafx.scene.DepthTest;
|
||||
import javafx.scene.Group;
|
||||
import javafx.scene.Node;
|
||||
import javafx.scene.PerspectiveCamera;
|
||||
import javafx.scene.SceneAntialiasing;
|
||||
import javafx.scene.SubScene;
|
||||
@ -23,7 +24,7 @@ import javafx.scene.input.ScrollEvent;
|
||||
import javafx.scene.paint.Color;
|
||||
import javafx.scene.paint.PhongMaterial;
|
||||
import javafx.scene.shape.Box;
|
||||
|
||||
import javafx.scene.shape.Shape3D;
|
||||
import javafx.scene.shape.Sphere;
|
||||
import javafx.scene.text.Text;
|
||||
import javafx.scene.transform.Rotate;
|
||||
@ -57,7 +58,7 @@ public class Array3DPane extends PamBorderPane {
|
||||
|
||||
public static final Color DEFAULT_HYDRO_COL = Color.RED;
|
||||
|
||||
// private static final Color DEFAULT_SENSOR_COL = Color.LIMEGREEN;
|
||||
// private static final Color DEFAULT_SENSOR_COL = Color.LIMEGREEN;
|
||||
|
||||
private double scaleFactor=20;
|
||||
|
||||
@ -97,23 +98,39 @@ public class Array3DPane extends PamBorderPane {
|
||||
* The size of the hydrophone for the 3D display.
|
||||
*/
|
||||
private double hydrophoneSize = 0.5;
|
||||
|
||||
|
||||
/**
|
||||
* Holds a list of hydrophone spheres
|
||||
*/
|
||||
private ArrayList<HydrophoneSphere> hydrophonesSpheres = new ArrayList<HydrophoneSphere>();
|
||||
|
||||
/**
|
||||
* Allow rotation
|
||||
*/
|
||||
private boolean allowRotate = true;
|
||||
|
||||
private Text xText;
|
||||
|
||||
private Text yText;
|
||||
|
||||
private Text zText;
|
||||
|
||||
private Box yAxis;
|
||||
|
||||
private Shape3D ySphere;
|
||||
|
||||
|
||||
public Array3DPane(){
|
||||
|
||||
// Create and position camera
|
||||
PerspectiveCamera camera = new PerspectiveCamera(true);
|
||||
camera.setFarClip(20000);
|
||||
camera.setNearClip(0.1);
|
||||
camera.setDepthTest(DepthTest.ENABLE);
|
||||
// camera.setDepthTest(DepthTest.ENABLE);
|
||||
camera.getTransforms().addAll (
|
||||
rotateY=new Rotate(-45, Rotate.Y_AXIS),
|
||||
rotateX=new Rotate(-45, Rotate.X_AXIS),
|
||||
translate=new Translate(0, 200, -2000));
|
||||
translate=new Translate(0, 0, -2000));
|
||||
|
||||
//create main 3D group
|
||||
root3D=new Group();
|
||||
@ -136,33 +153,33 @@ public class Array3DPane extends PamBorderPane {
|
||||
subScene.widthProperty().bind(this.widthProperty());
|
||||
subScene.heightProperty().bind(this.heightProperty());
|
||||
subScene.setDepthTest(DepthTest.ENABLE);
|
||||
|
||||
subScene.setOnMouseClicked((MouseEvent me) -> {
|
||||
mousePosX = me.getSceneX();
|
||||
mousePosY = me.getSceneY();
|
||||
PickResult pr = me.getPickResult();
|
||||
// System.out.println("Picked something sphere: " + pr);
|
||||
|
||||
//clear selected radius
|
||||
for (HydrophoneSphere sphere : hydrophonesSpheres) {
|
||||
sphere.setRadius(hydrophoneSize*scaleFactor);
|
||||
}
|
||||
|
||||
if(pr!=null && pr.getIntersectedNode() != null && pr.getIntersectedNode() instanceof Sphere){
|
||||
|
||||
//make the selected sphere slightly larger
|
||||
HydrophoneSphere s = (HydrophoneSphere) pr.getIntersectedNode();
|
||||
s.setRadius(hydrophoneSize*scaleFactor*1.2);
|
||||
|
||||
hydrophoneSelected(s.getHydrophone());
|
||||
|
||||
// System.out.println("Picked a sphere: " + pr);
|
||||
// distance=pr.getIntersectedDistance();
|
||||
// s = (Sphere) pr.getIntersectedNode();
|
||||
// isPicking=true;
|
||||
// vecIni = unProjectDirection(mousePosX, mousePosY, scene.getWidth(),scene.getHeight());
|
||||
}
|
||||
});
|
||||
subScene.setOnMouseClicked((MouseEvent me) -> {
|
||||
mousePosX = me.getSceneX();
|
||||
mousePosY = me.getSceneY();
|
||||
PickResult pr = me.getPickResult();
|
||||
// System.out.println("Picked something sphere: " + pr);
|
||||
|
||||
//clear selected radius
|
||||
for (HydrophoneSphere sphere : hydrophonesSpheres) {
|
||||
sphere.setRadius(hydrophoneSize*scaleFactor);
|
||||
}
|
||||
|
||||
if(pr!=null && pr.getIntersectedNode() != null && pr.getIntersectedNode() instanceof Sphere){
|
||||
|
||||
//make the selected sphere slightly larger
|
||||
HydrophoneSphere s = (HydrophoneSphere) pr.getIntersectedNode();
|
||||
s.setRadius(hydrophoneSize*scaleFactor*1.2);
|
||||
|
||||
hydrophoneSelected(s.getHydrophone());
|
||||
|
||||
// System.out.println("Picked a sphere: " + pr);
|
||||
// distance=pr.getIntersectedDistance();
|
||||
// s = (Sphere) pr.getIntersectedNode();
|
||||
// isPicking=true;
|
||||
// vecIni = unProjectDirection(mousePosX, mousePosY, scene.getWidth(),scene.getHeight());
|
||||
}
|
||||
});
|
||||
|
||||
//note the fill is actually quite important because if you don't have it mouse rotations etc
|
||||
//onyl work if you select a 3D shape
|
||||
@ -172,7 +189,7 @@ public class Array3DPane extends PamBorderPane {
|
||||
//handle mouse events for sub scene
|
||||
handleMouse(subScene);
|
||||
|
||||
|
||||
resetView();
|
||||
|
||||
//create new group to add sub scene to
|
||||
Group group = new Group();
|
||||
@ -208,7 +225,7 @@ public class Array3DPane extends PamBorderPane {
|
||||
* Create a 3D axis.
|
||||
* @param- size of the axis
|
||||
*/
|
||||
public static Group buildAxes(double axisSize, Color xAxisDiffuse, Color xAxisSpectacular,
|
||||
public Group buildAxes(double axisSize, Color xAxisDiffuse, Color xAxisSpectacular,
|
||||
Color yAxisDiffuse, Color yAxisSpectacular,
|
||||
Color zAxisDiffuse, Color zAxisSpectacular,
|
||||
Color textColour) {
|
||||
@ -230,18 +247,18 @@ public class Array3DPane extends PamBorderPane {
|
||||
blueMaterial.setDiffuseColor(zAxisDiffuse);
|
||||
blueMaterial.setSpecularColor(zAxisSpectacular);
|
||||
|
||||
Text xText=new Text("x");
|
||||
xText.setStyle("-fx-font: 20px Tahoma;");
|
||||
xText=new Text("x");
|
||||
xText.setStyle("-fx-font: 20px Tahoma; -fx-fill: white;");
|
||||
xText.setFill(textColour);
|
||||
xText.setStroke(textColour);
|
||||
|
||||
Text yText=new Text("z");
|
||||
yText.setStyle("-fx-font: 20px Tahoma; ");
|
||||
yText=new Text("z");
|
||||
yText.setStyle("-fx-font: 20px Tahoma; -fx-fill: white;");
|
||||
yText.setFill(textColour);
|
||||
yText.setStroke(textColour);
|
||||
|
||||
Text zText=new Text("y");
|
||||
zText.setStyle("-fx-font: 20px Tahoma; ");
|
||||
zText=new Text("y");
|
||||
zText.setStyle("-fx-font: 20px Tahoma; -fx-fill: white;");
|
||||
zText.setFill(textColour);
|
||||
zText.setStroke(textColour);
|
||||
|
||||
@ -254,7 +271,7 @@ public class Array3DPane extends PamBorderPane {
|
||||
zText.setTranslateZ(axisSize+5);
|
||||
|
||||
Sphere xSphere = new Sphere(radius);
|
||||
Sphere ySphere = new Sphere(radius);
|
||||
ySphere = new Sphere(radius);
|
||||
Sphere zSphere = new Sphere(radius);
|
||||
xSphere.setMaterial(redMaterial);
|
||||
ySphere.setMaterial(greenMaterial);
|
||||
@ -265,7 +282,7 @@ public class Array3DPane extends PamBorderPane {
|
||||
zSphere.setTranslateZ(axisSize);
|
||||
|
||||
Box xAxis = new Box(length, width, width);
|
||||
Box yAxis = new Box(width, length, width);
|
||||
yAxis = new Box(width, length, width);
|
||||
Box zAxis = new Box(width, width, length);
|
||||
xAxis.setMaterial(redMaterial);
|
||||
yAxis.setMaterial(greenMaterial);
|
||||
@ -302,6 +319,7 @@ public class Array3DPane extends PamBorderPane {
|
||||
|
||||
scene.setOnMouseDragged(new EventHandler<MouseEvent>() {
|
||||
|
||||
|
||||
@Override
|
||||
public void handle(MouseEvent me) {
|
||||
mouseOldX = mousePosX;
|
||||
@ -320,9 +338,11 @@ public class Array3DPane extends PamBorderPane {
|
||||
if (me.isShiftDown()) {
|
||||
modifier = 10.0;
|
||||
}
|
||||
if (me.isPrimaryButtonDown()) {
|
||||
if (me.isPrimaryButtonDown() && allowRotate) {
|
||||
rotateY.setAngle(rotateY.getAngle() + mouseDeltaX * modifierFactor * modifier * 2.0); // +
|
||||
rotateX.setAngle(rotateX.getAngle() - mouseDeltaY * modifierFactor * modifier * 2.0); // -
|
||||
|
||||
// System.out.println("Rotation: x: " + rotateX.getAngle() + " y: " + rotateY.getAngle());
|
||||
}
|
||||
if (me.isSecondaryButtonDown()) {
|
||||
translate.setX(translate.getX() -mouseDeltaX * modifierFactor * modifier * 5);
|
||||
@ -340,7 +360,7 @@ public class Array3DPane extends PamBorderPane {
|
||||
*/
|
||||
public void drawArray(PamArray array) {
|
||||
|
||||
// System.out.println("DRAW ARRAY: " + array);
|
||||
// System.out.println("DRAW ARRAY: " + array);
|
||||
|
||||
//clear the array
|
||||
arrayGroup.getChildren().removeAll(arrayGroup.getChildren());
|
||||
@ -352,13 +372,13 @@ public class Array3DPane extends PamBorderPane {
|
||||
Streamer streamer;
|
||||
hydrophonesSpheres.clear();
|
||||
for (int i=0; i<hydrophones.size(); i++){
|
||||
|
||||
|
||||
//get the streamer for the hydrophone
|
||||
streamer = array.getStreamer(hydrophones.get(i).getStreamerId());
|
||||
|
||||
double x = hydrophones.get(i).getX() + hydrophones.get(i).getStreamerId();
|
||||
double y = hydrophones.get(i).getY() + hydrophones.get(i).getStreamerId();
|
||||
double z = hydrophones.get(i).getZ() + hydrophones.get(i).getStreamerId();
|
||||
double x = (hydrophones.get(i).getX() + streamer.getCoordinate(0));
|
||||
double y = (hydrophones.get(i).getY() + streamer.getCoordinate(1));
|
||||
double z = -(hydrophones.get(i).getZ() + streamer.getCoordinate(2));
|
||||
|
||||
sphere=new HydrophoneSphere(hydrophoneSize*scaleFactor);
|
||||
sphere.setTranslateX(x*scaleFactor);
|
||||
@ -373,21 +393,21 @@ public class Array3DPane extends PamBorderPane {
|
||||
sphere.setMaterial(aMaterial);
|
||||
sphere.setHydrophone(hydrophones.get(i));
|
||||
|
||||
// System.out.println("Add hydrophone: " + x + " " + y + " " +z);
|
||||
// System.out.println("Add hydrophone: " + x + " " + y + " " +z);
|
||||
|
||||
hydrophonesSpheres.add(sphere);
|
||||
arrayGroup.getChildren().add(sphere);
|
||||
|
||||
|
||||
ArrayList<Point3D> streamerPoints=new ArrayList<Point3D>();
|
||||
//now plot a line from the streamer to the hydrophone
|
||||
Point3D newPoint;
|
||||
|
||||
|
||||
newPoint=new Point3D(x*scaleFactor, z*scaleFactor, y*scaleFactor);
|
||||
streamerPoints.add(newPoint);
|
||||
|
||||
newPoint =new Point3D(streamer.getCoordinate(0)*scaleFactor, streamer.getCoordinate(2)*scaleFactor, streamer.getCoordinate(1)*scaleFactor);
|
||||
|
||||
newPoint =new Point3D(streamer.getCoordinate(0)*scaleFactor, -streamer.getCoordinate(2)*scaleFactor, streamer.getCoordinate(1)*scaleFactor);
|
||||
streamerPoints.add(newPoint);
|
||||
|
||||
|
||||
System.out.println("Streamer points: " + streamerPoints.size());
|
||||
|
||||
PolyLine3D polyLine3D=new PolyLine3D(streamerPoints, 4f, Color.DODGERBLUE);
|
||||
@ -397,13 +417,13 @@ public class Array3DPane extends PamBorderPane {
|
||||
|
||||
|
||||
private class HydrophoneSphere extends Sphere {
|
||||
|
||||
|
||||
Hydrophone hydrophone;
|
||||
|
||||
|
||||
public Hydrophone getHydrophone() {
|
||||
return hydrophone;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
public void setHydrophone(Hydrophone hydrophone) {
|
||||
@ -413,13 +433,67 @@ public class Array3DPane extends PamBorderPane {
|
||||
public HydrophoneSphere() {
|
||||
super();
|
||||
}
|
||||
|
||||
|
||||
public HydrophoneSphere(double radius) {
|
||||
super(radius);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Sets the pane to show hydrophones in 2D or 3D.
|
||||
* @param set3D - true to set to 3D
|
||||
*/
|
||||
public void set3D(boolean set3D) {
|
||||
|
||||
double textRotation =0;
|
||||
|
||||
if (set3D) {
|
||||
allowRotate=true;
|
||||
xText.setRotate(0);
|
||||
rotateY.setAngle(-45);
|
||||
rotateX.setAngle(-45);
|
||||
}
|
||||
else {
|
||||
allowRotate=false;
|
||||
rotateY.setAngle(0);
|
||||
rotateX.setAngle(270);
|
||||
textRotation=-90;
|
||||
}
|
||||
|
||||
//confusing because the yaxis is the z axis in JavaFX...
|
||||
yText.setVisible(set3D);
|
||||
yAxis.setVisible(set3D);
|
||||
ySphere.setVisible(set3D);
|
||||
|
||||
|
||||
xText.setRotate(textRotation);
|
||||
xText.setRotationAxis(new javafx.geometry.Point3D(1,0,0));
|
||||
|
||||
yText.setRotationAxis(new javafx.geometry.Point3D(1,0,0));
|
||||
yText.setRotate(textRotation);
|
||||
|
||||
zText.setRotationAxis(new javafx.geometry.Point3D(1,0,0));
|
||||
zText.setRotate(textRotation);
|
||||
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Reset to the defulat view.
|
||||
*/
|
||||
public void resetView() {
|
||||
|
||||
translate.setX(0);
|
||||
translate.setY(0);
|
||||
translate.setZ( -2000);
|
||||
|
||||
if (allowRotate) {
|
||||
rotateY.setAngle(-45);
|
||||
rotateX.setAngle(-45);
|
||||
}
|
||||
}
|
||||
|
||||
// /**
|
||||
// * Draw the entire array
|
||||
// * @param pos - hydrophone and streamer positions in the same co-ordinate frame as the reference frame.
|
||||
|
@ -2,17 +2,23 @@ package Array.layoutFX;
|
||||
|
||||
import java.io.File;
|
||||
|
||||
import org.controlsfx.control.SegmentedButton;
|
||||
|
||||
import Array.ArrayManager;
|
||||
import Array.Hydrophone;
|
||||
import Array.PamArray;
|
||||
import PamController.PamController;
|
||||
import PamController.SettingsPane;
|
||||
import javafx.scene.Node;
|
||||
import javafx.scene.control.ContextMenu;
|
||||
import javafx.scene.control.Label;
|
||||
import javafx.scene.control.MenuItem;
|
||||
import javafx.scene.control.ToggleButton;
|
||||
import javafx.scene.control.Tooltip;
|
||||
import javafx.scene.layout.Pane;
|
||||
import javafx.scene.layout.Priority;
|
||||
import javafx.scene.layout.Region;
|
||||
import javafx.scene.layout.StackPane;
|
||||
import javafx.geometry.Insets;
|
||||
import javafx.geometry.Pos;
|
||||
import javafx.scene.layout.VBox;
|
||||
@ -35,7 +41,7 @@ import pamViewFX.fxNodes.PamHBox;
|
||||
*
|
||||
*/
|
||||
public class ArraySettingsPane extends SettingsPane<PamArray >{
|
||||
|
||||
|
||||
/**
|
||||
* Minimum size of the 3D pane.
|
||||
*/
|
||||
@ -50,15 +56,15 @@ public class ArraySettingsPane extends SettingsPane<PamArray >{
|
||||
* Pane for adding or removing streamers.
|
||||
*/
|
||||
private StreamersPane streamerPane;
|
||||
|
||||
|
||||
private PamBorderPane mainPane;
|
||||
|
||||
|
||||
/**
|
||||
* Pane for adding or removing hydrophones.
|
||||
*/
|
||||
private HydrophonesPane hydrophonePane;
|
||||
|
||||
// private Pane holder;
|
||||
// private Pane holder;
|
||||
|
||||
private Label hydrophoneLabel;
|
||||
|
||||
@ -83,16 +89,16 @@ public class ArraySettingsPane extends SettingsPane<PamArray >{
|
||||
|
||||
public ArraySettingsPane() {
|
||||
super(null);
|
||||
|
||||
|
||||
mainPane=new PamBorderPane();
|
||||
|
||||
|
||||
mainPane.setCenter(createArrayPane());
|
||||
// mainPane.setStyle("-fx-background-color: red;");
|
||||
// mainPane.setStyle("-fx-background-color: red;");
|
||||
mainPane.setMaxWidth(Double.MAX_VALUE);
|
||||
mainPane.setMinWidth(1100);
|
||||
mainPane.setStyle("-fx-padding: 0,0,0,0");
|
||||
|
||||
|
||||
|
||||
|
||||
recivierDiagramLabel = new Label("Hydrophone Diagram");
|
||||
PamGuiManagerFX.titleFont1style(recivierDiagramLabel);
|
||||
recivierDiagramLabel.setPadding(new Insets(5,5,5,5));
|
||||
@ -100,78 +106,123 @@ public class ArraySettingsPane extends SettingsPane<PamArray >{
|
||||
Label environmentLabel = new Label("Environment");
|
||||
PamGuiManagerFX.titleFont1style(environmentLabel);
|
||||
environmentLabel.setPadding(new Insets(0,0,5,0)); //little more space under this label
|
||||
|
||||
|
||||
environmentalPane = createEnvironmentPane();
|
||||
|
||||
|
||||
PamVBox rightPane = new PamVBox();
|
||||
rightPane.setSpacing(5);
|
||||
rightPane.getChildren().addAll(recivierDiagramLabel, create3DPane(), environmentLabel, new PamBorderPane(environmentalPane.getContentNode()));
|
||||
VBox.setVgrow(array3DPane, Priority.ALWAYS);
|
||||
|
||||
|
||||
Pane hydrophone3DPane = create3DPane();
|
||||
rightPane.getChildren().addAll(recivierDiagramLabel, hydrophone3DPane, environmentLabel, new PamBorderPane(environmentalPane.getContentNode()));
|
||||
VBox.setVgrow(hydrophone3DPane, Priority.ALWAYS);
|
||||
|
||||
mainPane.setRight(rightPane);
|
||||
|
||||
// streamerPane.getStreamerTable().getItems().addListener((ListChangeListener<? super StreamerProperty>) c->{
|
||||
// //the streamer table has changed and so the streamer needs changed
|
||||
// System.out.println("Streamer Changed!!!");
|
||||
// });
|
||||
|
||||
|
||||
// streamerPane.getStreamerTable().getItems().addListener((ListChangeListener<? super StreamerProperty>) c->{
|
||||
// //the streamer table has changed and so the streamer needs changed
|
||||
// System.out.println("Streamer Changed!!!");
|
||||
// });
|
||||
|
||||
streamerPane.addStreamerListener((x,y)->{
|
||||
PamArray array = getParams(new PamArray("temp_array: ", null)) ;
|
||||
System.out.println("Streamer changed!");
|
||||
array3DPane.drawArray(array);
|
||||
});
|
||||
|
||||
|
||||
hydrophonePane.addStreamerListener((x,y)->{
|
||||
PamArray array = getParams(new PamArray("temp_array: ", null)) ;
|
||||
System.out.println("Hydrophone changed!" + array.getHydrophoneCount());
|
||||
array3DPane.drawArray(array);
|
||||
});
|
||||
|
||||
// mainPane.setMinWidth(800);
|
||||
// mainPane.setMinWidth(800);
|
||||
|
||||
// mainPane.setCenter(createArrayPane());
|
||||
//
|
||||
// mainPane.getAdvPane().setCenter(new Label("Advanced Settings"));
|
||||
|
||||
|
||||
// //mainPane.getFront().setStyle("-fx-background-color: grey;");
|
||||
// mainPane.setStyle("-fx-background-color: red;");
|
||||
//
|
||||
// FlipPane aflipPane = new FlipPane();
|
||||
// aflipPane.setStyle("-fx-background-color: red;");
|
||||
//
|
||||
// PamHBox stackPane = new PamHBox();
|
||||
// stackPane.setStyle("-fx-background-color: red;");
|
||||
//
|
||||
// Button button = new Button();
|
||||
// button.setOnAction((action)->{
|
||||
// System.out.println(" 1 " + stackPane.getPadding());
|
||||
// System.out.println(" 2 " +PamBorderPane.getMargin(stackPane));
|
||||
// System.out.println(" 3 " + holder.getPadding());
|
||||
// });
|
||||
//
|
||||
// stackPane.getChildren().add(button);
|
||||
//
|
||||
//
|
||||
// mainPane.setPadding(new Insets(0,0,0,0));
|
||||
|
||||
|
||||
// holder = new StackPane();
|
||||
// holder.getChildren().add(mainPane);
|
||||
// holder.setStyle("-fx-padding: 0,0,0,0");
|
||||
// mainPane.setCenter(createArrayPane());
|
||||
//
|
||||
// mainPane.getAdvPane().setCenter(new Label("Advanced Settings"));
|
||||
|
||||
|
||||
// //mainPane.getFront().setStyle("-fx-background-color: grey;");
|
||||
// mainPane.setStyle("-fx-background-color: red;");
|
||||
//
|
||||
// FlipPane aflipPane = new FlipPane();
|
||||
// aflipPane.setStyle("-fx-background-color: red;");
|
||||
//
|
||||
// PamHBox stackPane = new PamHBox();
|
||||
// stackPane.setStyle("-fx-background-color: red;");
|
||||
//
|
||||
// Button button = new Button();
|
||||
// button.setOnAction((action)->{
|
||||
// System.out.println(" 1 " + stackPane.getPadding());
|
||||
// System.out.println(" 2 " +PamBorderPane.getMargin(stackPane));
|
||||
// System.out.println(" 3 " + holder.getPadding());
|
||||
// });
|
||||
//
|
||||
// stackPane.getChildren().add(button);
|
||||
//
|
||||
//
|
||||
// mainPane.setPadding(new Insets(0,0,0,0));
|
||||
|
||||
|
||||
// holder = new StackPane();
|
||||
// holder.getChildren().add(mainPane);
|
||||
// holder.setStyle("-fx-padding: 0,0,0,0");
|
||||
|
||||
}
|
||||
|
||||
private Pane create3DPane() {
|
||||
this.array3DPane = new HydrophoneArray3DPane();
|
||||
|
||||
//important because the 3D pane has not default size
|
||||
array3DPane.setMinWidth(MIN_3D_WIDTH);
|
||||
array3DPane.setMinHeight(MIN_3D_HEIGHT);
|
||||
|
||||
return array3DPane;
|
||||
StackPane stackPane = new StackPane();
|
||||
this.array3DPane = new HydrophoneArray3DPane();
|
||||
|
||||
//important because the 3D pane has not default size
|
||||
stackPane.setMinWidth(MIN_3D_WIDTH);
|
||||
stackPane.setMinHeight(MIN_3D_HEIGHT);
|
||||
|
||||
// stackPane.prefHeightProperty().bind(mainPane.heightProperty().subtract(100));
|
||||
|
||||
stackPane.getChildren().add(array3DPane);
|
||||
|
||||
|
||||
//add buttons
|
||||
ToggleButton b1 = new ToggleButton("2D");
|
||||
ToggleButton b2 = new ToggleButton("3D");
|
||||
|
||||
b1.setOnAction((action)->{
|
||||
array3DPane.set3D(false);
|
||||
});
|
||||
|
||||
b2.setOnAction((action)->{
|
||||
array3DPane.set3D(true);
|
||||
});
|
||||
|
||||
|
||||
SegmentedButton segmentedButton = new SegmentedButton();
|
||||
segmentedButton.getButtons().addAll(b1, b2);
|
||||
segmentedButton.setPadding(new Insets(5,5,5,5));
|
||||
segmentedButton.setMinWidth(100);
|
||||
|
||||
StackPane.setAlignment(segmentedButton, Pos.TOP_RIGHT);
|
||||
stackPane.getChildren().add(segmentedButton);
|
||||
|
||||
|
||||
final ContextMenu contextMenu = new ContextMenu();
|
||||
final MenuItem item1 = new MenuItem("Reset");
|
||||
item1.setOnAction((action)->{
|
||||
array3DPane.resetView();
|
||||
});
|
||||
contextMenu.getItems().add(item1);
|
||||
segmentedButton.setContextMenu(contextMenu);
|
||||
|
||||
// stackPane.setOnContextMenuRequested(e ->
|
||||
// contextMenu.show(stackPane, e.getScreenX(), e.getScreenY()));
|
||||
|
||||
|
||||
b2.setSelected(true);
|
||||
|
||||
return stackPane;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Create the environment pane.
|
||||
* @return the environment pane.
|
||||
@ -186,22 +237,22 @@ public class ArraySettingsPane extends SettingsPane<PamArray >{
|
||||
* @return the main array pane.
|
||||
*/
|
||||
private Pane createArrayPane() {
|
||||
|
||||
|
||||
Label arrayLabel = new Label("Array");
|
||||
arrayLabel.setPadding(new Insets(5,5,5,5));
|
||||
PamGuiManagerFX.titleFont1style(arrayLabel);
|
||||
|
||||
|
||||
//holds the array label and also some button for import and export.
|
||||
PamHBox arrayImportExportBox = new PamHBox();
|
||||
arrayImportExportBox.setSpacing(5);
|
||||
arrayImportExportBox.setAlignment(Pos.CENTER_LEFT);
|
||||
arrayImportExportBox.setPadding(new Insets(5,0,0,0));
|
||||
|
||||
fileChooser = new FileChooser();
|
||||
fileChooser.setTitle("Open Resource File");
|
||||
fileChooser.getExtensionFilters().addAll(
|
||||
new ExtensionFilter("PAMNGuard Array Files", "*.paf"));
|
||||
|
||||
|
||||
fileChooser = new FileChooser();
|
||||
fileChooser.setTitle("Open Resource File");
|
||||
fileChooser.getExtensionFilters().addAll(
|
||||
new ExtensionFilter("PAMNGuard Array Files", "*.paf"));
|
||||
|
||||
PamButton importButton = new PamButton("Import...");
|
||||
importButton.setOnAction((action)->{
|
||||
importArray();
|
||||
@ -215,13 +266,13 @@ public class ArraySettingsPane extends SettingsPane<PamArray >{
|
||||
});
|
||||
exportButton.setGraphic(PamGlyphDude.createPamIcon("mdi2f-file-export", PamGuiManagerFX.iconSize));
|
||||
exportButton.setTooltip(new Tooltip("Export array settings to a .pgaf file"));
|
||||
|
||||
|
||||
//balnk region to make it look nicer
|
||||
Region blank = new Region();
|
||||
blank.setPrefWidth(70);
|
||||
|
||||
|
||||
arrayImportExportBox.getChildren().addAll(importButton, exportButton, blank);
|
||||
|
||||
|
||||
PamBorderPane titleHolder = new PamBorderPane();
|
||||
titleHolder.setLeft(arrayLabel);
|
||||
titleHolder.setRight(arrayImportExportBox);
|
||||
@ -229,25 +280,25 @@ public class ArraySettingsPane extends SettingsPane<PamArray >{
|
||||
//the streamer pane for changing streamer settings.
|
||||
streamerPane = new StreamersPane();
|
||||
streamerPane.setMaxWidth(Double.MAX_VALUE);
|
||||
|
||||
|
||||
hydrophoneLabel = new Label("Hydrophones");
|
||||
PamGuiManagerFX.titleFont1style(hydrophoneLabel);
|
||||
hydrophoneLabel.setPadding(new Insets(5,5,5,5));
|
||||
|
||||
|
||||
hydrophonePane = new HydrophonesPane();
|
||||
hydrophonePane.setMaxWidth(Double.MAX_VALUE);
|
||||
|
||||
// PamButton advancedButton = new PamButton();
|
||||
// advancedButton.setOnAction((action)->{
|
||||
// mainPane.flipToBack();
|
||||
// });
|
||||
// advancedButton.setGraphic(PamGlyphDude.createPamIcon("mdi2c-cog"));
|
||||
// PamButton advancedButton = new PamButton();
|
||||
// advancedButton.setOnAction((action)->{
|
||||
// mainPane.flipToBack();
|
||||
// });
|
||||
// advancedButton.setGraphic(PamGlyphDude.createPamIcon("mdi2c-cog"));
|
||||
|
||||
// PamHBox advancedPane = new PamHBox();
|
||||
// advancedPane.setSpacing(5);
|
||||
// advancedPane.setAlignment(Pos.CENTER_RIGHT);
|
||||
// advancedPane.getChildren().addAll(new Label("Advanced"), advancedButton);
|
||||
|
||||
// PamHBox advancedPane = new PamHBox();
|
||||
// advancedPane.setSpacing(5);
|
||||
// advancedPane.setAlignment(Pos.CENTER_RIGHT);
|
||||
// advancedPane.getChildren().addAll(new Label("Advanced"), advancedButton);
|
||||
|
||||
PamVBox vBox = new PamVBox();
|
||||
vBox.setSpacing(5);
|
||||
vBox.getChildren().addAll(titleHolder, streamerPane, hydrophoneLabel,
|
||||
@ -285,34 +336,34 @@ public class ArraySettingsPane extends SettingsPane<PamArray >{
|
||||
private void setReceieverLabels() {
|
||||
hydrophonePane.setRecieverLabels();
|
||||
streamerPane.setRecieverLabels();
|
||||
|
||||
|
||||
hydrophoneLabel.setText(PamController.getInstance().getGlobalMediumManager().getRecieverString(true) + "s");
|
||||
recivierDiagramLabel.setText(PamController.getInstance().getGlobalMediumManager().getRecieverString(true) + " diagram");
|
||||
// if (singleInstance!=null) {
|
||||
// singleInstance.setTitle("Pamguard "+ PamController.getInstance().getGlobalMediumManager().getRecieverString(false) +" array");
|
||||
// }
|
||||
// if (singleInstance!=null) {
|
||||
// singleInstance.setTitle("Pamguard "+ PamController.getInstance().getGlobalMediumManager().getRecieverString(false) +" array");
|
||||
// }
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
@Override
|
||||
public PamArray getParams(PamArray currParams) {
|
||||
currParams = streamerPane.getParams(currParams);
|
||||
currParams = hydrophonePane.getParams(currParams);
|
||||
currParams.setHydrophoneInterpolation(hydrophonePane.getHydrophoneInterp());
|
||||
currParams = environmentalPane.getParams(currParams);
|
||||
// System.out.println("Array settings pane: No. streamers: " + currParams.getStreamerCount());
|
||||
// System.out.println("Array settings pane: No. streamers: " + currParams.getStreamerCount());
|
||||
return currParams;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setParams(PamArray input) {
|
||||
this.currentArray = input.clone();
|
||||
// System.out.println("Hydrophone array is: "+ input);
|
||||
// System.out.println("Hydrophone array is: "+ input);
|
||||
setReceieverLabels();
|
||||
hydrophonePane.setParams(input);
|
||||
streamerPane.setParams(input);
|
||||
environmentalPane.setParams(input);
|
||||
|
||||
|
||||
//draw the array
|
||||
array3DPane.drawArray(input);
|
||||
}
|
||||
@ -331,16 +382,16 @@ public class ArraySettingsPane extends SettingsPane<PamArray >{
|
||||
@Override
|
||||
public void paneInitialized() {
|
||||
// TODO Auto-generated method stub
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
private class HydrophoneArray3DPane extends Array3DPane {
|
||||
|
||||
|
||||
@Override
|
||||
public void hydrophoneSelected(Hydrophone hydrophone) {
|
||||
hydrophonePane.selectHydrophone(hydrophone);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -82,7 +82,7 @@ public class HydrophonesPane extends PamBorderPane {
|
||||
tableArrayPane.setPadding(new Insets(5,5,5,5));
|
||||
|
||||
pamFlipePane = new PamFlipPane();
|
||||
pamFlipePane.getAdvLabel().setText("Hydrophone Settings");
|
||||
pamFlipePane.getAdvLabel().setText(PamController.getInstance().getGlobalMediumManager().getRecieverString());
|
||||
// pamFlipePane.minWidthProperty().bind(this.widthProperty());
|
||||
// pamFlipePane.setStyle("-fx-background-color: green;");
|
||||
|
||||
|
@ -109,10 +109,13 @@ public class CPODBinaryStore extends BinaryDataSource {
|
||||
|
||||
|
||||
private void writeCPODData(DataOutputStream dos2, CPODClick cd) throws IOException {
|
||||
|
||||
//CPOD has 8 bytes - FPOD has more
|
||||
dos.writeInt(cd.getRawData().length);
|
||||
for (int i=0; i<cd.getRawData().length; i++) {
|
||||
dos.writeShort(cd.getRawData()[i]);
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -7,6 +7,9 @@ import PamguardMVC.PamDataBlock;
|
||||
import PamguardMVC.PamDataUnit;
|
||||
import PamguardMVC.superdet.SuperDetection;
|
||||
|
||||
/**
|
||||
* CPOD click.
|
||||
*/
|
||||
public class CPODClick extends PamDataUnit<PamDataUnit,SuperDetection> implements AcousticDataUnit {
|
||||
|
||||
private short nCyc;
|
||||
@ -57,6 +60,7 @@ public class CPODClick extends PamDataUnit<PamDataUnit,SuperDetection> implement
|
||||
int t = shortData[0]<<16 |
|
||||
shortData[1]<<8 |
|
||||
shortData[2]; // 5 microsec intervals !
|
||||
|
||||
long tMillis = minuteMillis + t/200;
|
||||
// now a bit of time stretching. Need to get the start time and see how
|
||||
// different this is, then it's a linear stretch.
|
||||
@ -90,6 +94,7 @@ public class CPODClick extends PamDataUnit<PamDataUnit,SuperDetection> implement
|
||||
shortData[1]<<8 |
|
||||
shortData[2]; // 5 microsec intervals !
|
||||
long tMillis = minuteMillis + t/200;
|
||||
|
||||
// now a bit of time stretching. Need to get the start time and see how
|
||||
// different this is, then it's a linear stretch.
|
||||
tMillis = cpodControl.stretchClicktime(tMillis);
|
||||
@ -137,8 +142,11 @@ public class CPODClick extends PamDataUnit<PamDataUnit,SuperDetection> implement
|
||||
//estimate the duration in millis - not accurate but gives an idea.
|
||||
double duration = (nCyc/(double) kHz);
|
||||
this.setDurationInMilliseconds(duration);
|
||||
|
||||
this.rawData = shortData.clone();
|
||||
|
||||
if (shortData!=null) {
|
||||
//only CPOD
|
||||
this.rawData = shortData.clone();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -91,7 +91,7 @@ public class CPODControl extends OfflineFileControl implements PamSettings {
|
||||
* @return milliseconds.
|
||||
*/
|
||||
public static long podTimeToMillis(long podTime) {
|
||||
return podTime * 60L * 1000L - (25569L*3600L*24000L);
|
||||
return CPODUtils.podTimeToMillis(podTime);
|
||||
}
|
||||
|
||||
public long stretchClicktime(long rawTime) {
|
||||
|
@ -3,6 +3,7 @@ package cpod;
|
||||
import java.awt.Frame;
|
||||
import java.io.File;
|
||||
import java.io.Serializable;
|
||||
import java.util.List;
|
||||
|
||||
import javax.swing.JMenuItem;
|
||||
|
||||
@ -21,10 +22,11 @@ import cpod.fx.CPODGUIFX;
|
||||
import cpod.fx.CPODSettingsPane;
|
||||
import dataPlotsFX.data.TDDataProviderRegisterFX;
|
||||
import fileOfflineData.OfflineFileParams;
|
||||
import javafx.concurrent.Task;
|
||||
import pamViewFX.fxNodes.pamDialogFX.PamDialogFX2AWT;
|
||||
|
||||
/**
|
||||
* CPOD control. Loads and manages CPOD (and hopefully soon FPOD) data into
|
||||
* CPOD control. Loads and manages CPOD and FPOD data into
|
||||
* PAMGaurd.
|
||||
* <p>
|
||||
* Note that this module (CPODControl) originally used a folder of CP1 files as it's file store but
|
||||
@ -83,7 +85,7 @@ public class CPODControl2 extends PamControlledUnit implements PamSettings {
|
||||
* CPOD importer.
|
||||
*/
|
||||
private CPODImporter cpodImporter;
|
||||
|
||||
|
||||
|
||||
public CPODControl2(String unitName) {
|
||||
super("CPOD", unitName);
|
||||
@ -101,6 +103,7 @@ public class CPODControl2 extends PamControlledUnit implements PamSettings {
|
||||
// add the CP3 data block
|
||||
cpodProcess.addOutputDataBlock(cp3DataBlock = new CPODClickDataBlock("CP3 Data",
|
||||
cpodProcess, CPODMap.FILE_CP3));
|
||||
|
||||
cp3DataBlock.setPamSymbolManager(new CPODSymbolManager(this, cp3DataBlock));
|
||||
cp3DataBlock.setDatagramProvider(cpodDataGramProvider[1] = new CPODDataGramProvider(this));
|
||||
cp3DataBlock.setBinaryDataSource(new CPODBinaryStore(this, cp1DataBlock));
|
||||
@ -112,7 +115,6 @@ public class CPODControl2 extends PamControlledUnit implements PamSettings {
|
||||
|
||||
cpodImporter = new CPODImporter(this);
|
||||
|
||||
|
||||
//FX display data providers
|
||||
CPODPlotProviderFX cpodPlotProviderFX = new CPODPlotProviderFX(this, cp1DataBlock);
|
||||
TDDataProviderRegisterFX.getInstance().registerDataInfo(cpodPlotProviderFX);
|
||||
@ -146,19 +148,6 @@ public class CPODControl2 extends PamControlledUnit implements PamSettings {
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Convert POD time to JAVA millis - POD time is
|
||||
* integer minutes past the same epoc as Windows uses
|
||||
* i.e. 0th January 1900.
|
||||
* @param podTime
|
||||
* @return milliseconds.
|
||||
*/
|
||||
public static long podTimeToMillis(long podTime) {
|
||||
return podTime * 60L * 1000L - (25569L*3600L*24000L);
|
||||
}
|
||||
|
||||
public long stretchClicktime(long rawTime) {
|
||||
if (cp1DataBlock.getDatagrammedMap() == null) {
|
||||
return rawTime;
|
||||
@ -213,9 +202,6 @@ public class CPODControl2 extends PamControlledUnit implements PamSettings {
|
||||
|
||||
/**** GUI ****/
|
||||
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Get the settings pane.
|
||||
*
|
||||
@ -302,4 +288,13 @@ public class CPODControl2 extends PamControlledUnit implements PamSettings {
|
||||
return cpodImporter;
|
||||
}
|
||||
|
||||
/**
|
||||
* Import POD data. This will either be a list of CPOD or FPOD files.
|
||||
* @param files - the files to import.
|
||||
* @return a list of import Tasks.
|
||||
*/
|
||||
public List<Task<Integer>> importPODData(List<File> files) {
|
||||
return cpodImporter.importCPODData(files);
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -24,10 +24,11 @@ import binaryFileStorage.BinaryFooter;
|
||||
import binaryFileStorage.BinaryObjectData;
|
||||
import binaryFileStorage.BinaryOutputStream;
|
||||
import binaryFileStorage.BinaryStore;
|
||||
import cpod.FPODReader.FPODdata;
|
||||
import javafx.concurrent.Task;
|
||||
|
||||
/**
|
||||
* Imports data CPOD data and converts into binary files.
|
||||
* Imports FPOD and CPOD data and converts into binary files.
|
||||
*
|
||||
* @author Jamie Macaulay
|
||||
*
|
||||
@ -61,7 +62,7 @@ public class CPODImporter {
|
||||
CPODFileType cpFileType = CPODFileType.CP1;
|
||||
|
||||
/**
|
||||
* Hnadles the queue for importing files tasks
|
||||
* Handles the queue for importing files tasks
|
||||
*/
|
||||
private ExecutorService exec = Executors.newSingleThreadExecutor(r -> {
|
||||
Thread t = new Thread(r);
|
||||
@ -76,9 +77,9 @@ public class CPODImporter {
|
||||
*/
|
||||
public enum CPODFileType {
|
||||
CP1("CP1"),
|
||||
CP3("CP3");
|
||||
// FP1("fp1"),
|
||||
// FP3("fp3");
|
||||
CP3("CP3"),
|
||||
FP1("FP1"),
|
||||
FP3("FP3");
|
||||
|
||||
private String text;
|
||||
|
||||
@ -110,7 +111,7 @@ public class CPODImporter {
|
||||
|
||||
public static CPODFileType getFileType(File cpFile) {
|
||||
for (int i=0; i<CPODFileType.values().length; i++) {
|
||||
if (cpFile.getAbsolutePath().toLowerCase().endsWith(CPODFileType.values()[i].getText())) {
|
||||
if (cpFile.getAbsolutePath().toLowerCase().endsWith(CPODFileType.values()[i].getText().toLowerCase())) {
|
||||
return CPODFileType.values()[i];
|
||||
}
|
||||
}
|
||||
@ -124,6 +125,10 @@ public class CPODImporter {
|
||||
return 360;
|
||||
case CP3:
|
||||
return 720;
|
||||
case FP1:
|
||||
return 1024;
|
||||
case FP3:
|
||||
return 1024;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
@ -134,6 +139,10 @@ public class CPODImporter {
|
||||
return 10;
|
||||
case CP3:
|
||||
return 40;
|
||||
case FP1:
|
||||
return 16;
|
||||
case FP3:
|
||||
return 32;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
@ -154,15 +163,113 @@ public class CPODImporter {
|
||||
protected int importFile(File cpFile, CPODClickDataBlock dataBlock) {
|
||||
return importFile( cpFile, dataBlock, -1, Integer.MAX_VALUE);
|
||||
}
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Import a file.
|
||||
* @param cpFile - the CP1 file.
|
||||
* Import a CPOD or FPOD file.
|
||||
* @param cpFile - the CP1/FP1 or CP3/FP3 file.
|
||||
* @param from - the click index to save from. e.g. 100 means that only click 100 + in the file is saved
|
||||
* @param maxNum
|
||||
* @return the total number of clicks int he file.
|
||||
* @param maxNum - the maximum number to import
|
||||
* @return the total number of clicks in the file.
|
||||
*/
|
||||
protected int importFile(File cpFile, CPODClickDataBlock dataBlock, int from, int maxNum) {
|
||||
CPODFileType fileType = getFileType( cpFile);
|
||||
|
||||
switch (fileType) {
|
||||
case CP1:
|
||||
case CP3:
|
||||
return importCPODFile(cpFile, dataBlock, from, maxNum);
|
||||
case FP1:
|
||||
case FP3:
|
||||
return importFPODFile(cpFile, dataBlock, from, maxNum);
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Import a FPOD file.
|
||||
* @param cpFile - the FP1 or FP3 file.
|
||||
* @param from - the click index to save from. e.g. 100 means that only click 100 + in the file is saved
|
||||
* @param maxNum - the maximum number to import
|
||||
* @return the total number of clicks in the file.
|
||||
*/
|
||||
protected int importFPODFile(File cpFile, CPODClickDataBlock dataBlock, int from, int maxNum) {
|
||||
|
||||
ArrayList<FPODdata> fpodData = new ArrayList<FPODdata>();
|
||||
|
||||
try {
|
||||
FPODReader.importFile(cpFile, fpodData, from, maxNum);
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
|
||||
// fileStart + nMinutes * 60000L;
|
||||
|
||||
|
||||
int nClicks = 0;
|
||||
for (int i=0; i<fpodData.size(); i++) {
|
||||
//System.out.println("Create a new CPOD click: ");
|
||||
CPODClick cpodClick = processClick(fpodData.get(i));
|
||||
dataBlock.addPamData(cpodClick);
|
||||
nClicks++;
|
||||
}
|
||||
|
||||
fpodData=null; //trigger garbage collector if needed
|
||||
|
||||
return nClicks;
|
||||
}
|
||||
|
||||
/**
|
||||
* Process the click.
|
||||
* @param FPODData - an FPOD data object
|
||||
* @return
|
||||
*/
|
||||
private CPODClick processClick(FPODdata fpoDdata) {
|
||||
|
||||
//how many samples are we into the clicks
|
||||
|
||||
long fileSamples = (long) (((fpoDdata.minute*60) + (fpoDdata.FiveMusec*5/1000000.))*CPODClickDataBlock.CPOD_SR);
|
||||
|
||||
short[] data = new short[9];
|
||||
|
||||
short nCyc = (short) fpoDdata.Ncyc;
|
||||
short bw = (short) fpoDdata.BW;
|
||||
short kHz = (short) FPODReader.IPItoKhz(fpoDdata.IPIatMax);
|
||||
short endF = (short) FPODReader.IPItoKhz(fpoDdata.EndIPI);
|
||||
short spl = (short) fpoDdata.MaxPkExtnd;
|
||||
short slope = 0;
|
||||
|
||||
data[3]=nCyc;
|
||||
data[4]=bw;
|
||||
data[5]=kHz;
|
||||
data[6]=endF;
|
||||
data[7]=spl;
|
||||
data[8]=slope;
|
||||
|
||||
|
||||
CPODClick cpodClick = new CPODClick(fpoDdata.getTimeMillis(),
|
||||
fileSamples, nCyc, bw,
|
||||
kHz, endF, spl, slope, data);
|
||||
|
||||
|
||||
|
||||
return cpodClick;
|
||||
}
|
||||
|
||||
/**
|
||||
* Import a CPOD file.
|
||||
* @param cpFile - the CP1 or CP3 file.
|
||||
* @param from - the click index to save from. e.g. 100 means that only click 100 + in the file is saved
|
||||
* @param maxNum - the maximum number to import
|
||||
* @return the total number of clicks in the file.
|
||||
*/
|
||||
protected int importCPODFile(File cpFile, CPODClickDataBlock dataBlock, int from, int maxNum) {
|
||||
|
||||
BufferedInputStream bis = null;
|
||||
int bytesRead;
|
||||
FileInputStream fileInputStream = null;
|
||||
@ -190,7 +297,7 @@ public class CPODImporter {
|
||||
while (true) {
|
||||
bytesRead = bis.read(byteData);
|
||||
for (int i = 0; i < bytesRead; i++) {
|
||||
shortData[i] = toUnsigned(byteData[i]);
|
||||
shortData[i] = CPODUtils.toUnsigned(byteData[i]);
|
||||
}
|
||||
if (isFileEnd(byteData)) {
|
||||
fileEnds++;
|
||||
@ -215,7 +322,7 @@ public class CPODImporter {
|
||||
|
||||
}
|
||||
|
||||
// // now remove the data unit from the data block in order to clear up memory. Note that the remove method
|
||||
// // now remove the data unit from the data block in order to clear up memory. Note that the remove method
|
||||
// // saves the data unit to the Deleted-Items list, so clear that as well (otherwise we'll just be using
|
||||
// // up all the memory with that one)
|
||||
// dataBlock.remove(cpodClick);
|
||||
@ -235,6 +342,15 @@ public class CPODImporter {
|
||||
|
||||
return nClicks;
|
||||
}
|
||||
|
||||
|
||||
private CPODClick processClick(int nMinutes, short[] shortData) {
|
||||
/*
|
||||
*
|
||||
*/
|
||||
return CPODClick.makeClick(cpodControl, fileStart + nMinutes * 60000L, shortData);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* A new minute. Don;t think we need to do anything here.?
|
||||
@ -245,26 +361,7 @@ public class CPODImporter {
|
||||
|
||||
}
|
||||
|
||||
private CPODClick processClick(int nMinutes, short[] shortData) {
|
||||
/*
|
||||
*
|
||||
*/
|
||||
return CPODClick.makeClick(cpodControl, fileStart + nMinutes * 60000L, shortData);
|
||||
}
|
||||
|
||||
/**
|
||||
* Java will only have read signed bytes. Nick clearly
|
||||
* uses a lot of unsigned data, so convert and inflate to int16.
|
||||
* @param signedByte
|
||||
* @return unsigned version as int16.
|
||||
*/
|
||||
static short toUnsigned(byte signedByte) {
|
||||
short ans = signedByte;
|
||||
if (ans < 0) {
|
||||
ans += 256;
|
||||
}
|
||||
return ans;
|
||||
}
|
||||
|
||||
/**
|
||||
* Is it the end of the file ?
|
||||
@ -363,8 +460,10 @@ public class CPODImporter {
|
||||
public CPODClickDataBlock getDataBlock(CPODFileType type) {
|
||||
switch (type) {
|
||||
case CP1:
|
||||
case FP1:
|
||||
return this.cpodControl.getCP1DataBlock();
|
||||
case CP3:
|
||||
case FP3:
|
||||
return this.cpodControl.getCP3DataBlock();
|
||||
}
|
||||
return null;
|
||||
|
@ -29,6 +29,7 @@ public class CPODMap {
|
||||
|
||||
public static final int FILE_CP1 = 1;
|
||||
public static final int FILE_CP3 = 3;
|
||||
|
||||
int cpFileType = 0;
|
||||
|
||||
|
||||
|
37
src/cpod/CPODUtils.java
Normal file
37
src/cpod/CPODUtils.java
Normal file
@ -0,0 +1,37 @@
|
||||
package cpod;
|
||||
|
||||
/**
|
||||
* Some useful utility function for CPOD and FPOD data
|
||||
*/
|
||||
public class CPODUtils {
|
||||
|
||||
/**
|
||||
* Java will only have read signed bytes. Nick clearly
|
||||
* uses a lot of unsigned data, so convert and inflate to int16.
|
||||
* @param signedByte
|
||||
* @return unsigned version as int16.
|
||||
*/
|
||||
public static short toUnsigned(byte signedByte) {
|
||||
// short ans = signedByte;
|
||||
|
||||
short ans = (short) (signedByte & 0xff);
|
||||
|
||||
// if (ans < 0) {
|
||||
// ans += 256;
|
||||
// }
|
||||
|
||||
return ans;
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert POD time to JAVA millis - POD time is
|
||||
* integer minutes past the same epoc as Windows uses
|
||||
* i.e. 0th January 1900.
|
||||
* @param podTime
|
||||
* @return milliseconds.
|
||||
*/
|
||||
public static long podTimeToMillis(long podTime) {
|
||||
return podTime * 60L * 1000L - (25569L*3600L*24000L);
|
||||
}
|
||||
|
||||
}
|
1094
src/cpod/FPODReader.java
Normal file
1094
src/cpod/FPODReader.java
Normal file
File diff suppressed because it is too large
Load Diff
@ -64,7 +64,8 @@ public class CPODSettingsPane extends SettingsPane<CPODParams> {
|
||||
/**
|
||||
* The extension filter. Holds the types of files that can be imported.
|
||||
*/
|
||||
private ExtensionFilter extensionFilter;
|
||||
private FileChooser.ExtensionFilter extensionFilterCPOD;
|
||||
// private FileChooser.ExtensionFilter extensionFilterFPOD;
|
||||
|
||||
|
||||
/**
|
||||
@ -110,6 +111,10 @@ public class CPODSettingsPane extends SettingsPane<CPODParams> {
|
||||
super(null);
|
||||
this.cpodControl = cpodControl2;
|
||||
|
||||
|
||||
//define the types of files to be imported ("Note: add FP1 and FP3 here)
|
||||
extensionFilterCPOD = new ExtensionFilter("CPOD file", "*.cp1", "*.cp3", "*.fp1", "*.fp3");
|
||||
|
||||
//file chooser
|
||||
fileChooser = new FileChooser();
|
||||
fileChooser.getExtensionFilters().addAll(getExtensionFilters());
|
||||
@ -117,8 +122,6 @@ public class CPODSettingsPane extends SettingsPane<CPODParams> {
|
||||
//folder chooser
|
||||
folderChooser = new DirectoryChooser();
|
||||
|
||||
//define the types of files to be imported ("Note: add FP1 and FP3 here)
|
||||
extensionFilter = new ExtensionFilter("CPOD file", "*.cp1", "*.cp3");
|
||||
|
||||
|
||||
pathLabel = new TextField("No classifier file selected");
|
||||
@ -130,7 +133,7 @@ public class CPODSettingsPane extends SettingsPane<CPODParams> {
|
||||
// PamButton browsFileButton = new PamButton("", PamGlyphDude.createPamGlyph(MaterialDesignIcon.FILE_MULTIPLE, PamGuiManagerFX.iconSize));
|
||||
PamButton browsFileButton = new PamButton("", PamGlyphDude.createPamIcon("mdi2f-file-multiple", PamGuiManagerFX.iconSize));
|
||||
browsFileButton.setMinWidth(30);
|
||||
browsFileButton.setTooltip(new Tooltip("Browse to select a CP1 or CP3 file"));
|
||||
browsFileButton.setTooltip(new Tooltip("Browse to select individual or mutliple CP1 or CP3 files or FP1 or FP3 files"));
|
||||
browsFileButton.setOnAction((action)->{
|
||||
|
||||
List<File> files = fileChooser.showOpenMultipleDialog(this.getFXWindow());
|
||||
@ -145,7 +148,7 @@ public class CPODSettingsPane extends SettingsPane<CPODParams> {
|
||||
// PamButton browsFolderButton = new PamButton("", PamGlyphDude.createPamGlyph(MaterialDesignIcon.FOLDER, PamGuiManagerFX.iconSize));
|
||||
PamButton browsFolderButton = new PamButton("", PamGlyphDude.createPamIcon("mdi2f-folder", PamGuiManagerFX.iconSize));
|
||||
browsFolderButton.setMinWidth(30);
|
||||
browsFolderButton.setTooltip(new Tooltip("Browse to a folder containg CP1 and CP3 files"));
|
||||
browsFolderButton.setTooltip(new Tooltip("Browse to a folder contaning CP1 and CP3 or FP1 and FP3 files"));
|
||||
browsFolderButton.setOnAction((action)->{
|
||||
|
||||
File file = folderChooser.showDialog(this.getFXWindow());
|
||||
@ -168,7 +171,7 @@ public class CPODSettingsPane extends SettingsPane<CPODParams> {
|
||||
pathLabel.setMaxWidth(Double.MAX_VALUE);
|
||||
pathLabel.prefHeightProperty().bind(browsFolderButton.heightProperty());
|
||||
|
||||
filesPane.getChildren().addAll(pathLabel, browsFolderButton);
|
||||
filesPane.getChildren().addAll(pathLabel, browsFileButton, browsFolderButton);
|
||||
|
||||
//time offset pane.
|
||||
startOffset = new PamSpinner<Double>();
|
||||
@ -296,7 +299,8 @@ public class CPODSettingsPane extends SettingsPane<CPODParams> {
|
||||
System.out.println("Import CPOD data: " + files.size());
|
||||
|
||||
//begins the import
|
||||
this.tasks = this.cpodControl.getCpodImporter().importCPODData(files);
|
||||
// this.tasks = this.cpodControl.getCpodImporter().importCPODData(files);
|
||||
this.tasks = this.cpodControl.importPODData(files);
|
||||
|
||||
if (tasks ==null) return false;
|
||||
|
||||
@ -428,8 +432,13 @@ public class CPODSettingsPane extends SettingsPane<CPODParams> {
|
||||
* new ExtensionFilter("Pytorch Model", "*.pk")
|
||||
* @return a list of extension fitlers for the file dialog.
|
||||
*/
|
||||
public ExtensionFilter getExtensionFilters(){
|
||||
return extensionFilter;
|
||||
public ArrayList<FileChooser.ExtensionFilter> getExtensionFilters(){
|
||||
ArrayList<FileChooser.ExtensionFilter> filters = new ArrayList<FileChooser.ExtensionFilter>();
|
||||
filters.add(extensionFilterCPOD);
|
||||
//don't add an exstra filter - just have all as one - otherwise the user has to change the
|
||||
//file dialog to FPODs to get it to work.
|
||||
// filters.add(extensionFilterFPOD);
|
||||
return filters;
|
||||
}
|
||||
|
||||
|
||||
|
@ -4,7 +4,6 @@ import java.util.ArrayList;
|
||||
|
||||
import PamController.PamController;
|
||||
import PamModel.PamModuleInfo;
|
||||
import atlantafx.base.theme.PrimerDark;
|
||||
import dataModelFX.ConnectionNodeParams.PAMConnectionNodeType;
|
||||
import dataModelFX.connectionNodes.ModuleIconFactory;
|
||||
import javafx.beans.property.ObjectProperty;
|
||||
@ -13,7 +12,6 @@ import javafx.event.EventHandler;
|
||||
import javafx.geometry.Insets;
|
||||
import javafx.scene.Node;
|
||||
import javafx.scene.SnapshotParameters;
|
||||
import javafx.scene.control.Button;
|
||||
import javafx.scene.control.Tooltip;
|
||||
import javafx.scene.image.ImageView;
|
||||
import javafx.scene.input.ClipboardContent;
|
||||
@ -29,7 +27,6 @@ import pamViewFX.fxNodes.PamTilePane;
|
||||
import pamViewFX.fxNodes.PamTitledPane;
|
||||
import pamViewFX.fxNodes.PamVBox;
|
||||
import pamViewFX.fxNodes.connectionPane.structures.ConnectionGroupBody;
|
||||
import pamViewFX.fxNodes.connectionPane.structures.ConnectionStructure.ConnectionStructureType;
|
||||
import pamViewFX.fxStyles.PamStylesManagerFX;
|
||||
import pamViewFX.fxNodes.connectionPane.structures.ExtensionSocketStructure;
|
||||
|
||||
|
@ -20,8 +20,6 @@ import userDisplayFX.UserDisplayNodeFX;
|
||||
import PamModel.PamModel;
|
||||
import PamModel.PamModuleInfo;
|
||||
import PamView.PamViewInterface;
|
||||
import atlantafx.base.theme.PrimerDark;
|
||||
import atlantafx.base.theme.PrimerLight;
|
||||
import dataMap.layoutFX.DataMapPaneFX;
|
||||
import PamController.PAMControllerGUI;
|
||||
import PamController.PamControlledUnit;
|
||||
|
@ -27,6 +27,7 @@ import pamViewFX.fxNodes.pamDialogFX.PamDialogFX2AWT;
|
||||
import rawDeepLearningClassifier.dataPlotFX.DLDetectionPlotProvider;
|
||||
import rawDeepLearningClassifier.dataPlotFX.DLPredictionProvider;
|
||||
import rawDeepLearningClassifier.ddPlotFX.RawDLDDPlotProvider;
|
||||
import rawDeepLearningClassifier.defaultModels.DLDefaultModelManager;
|
||||
import rawDeepLearningClassifier.dlClassification.DLClassName;
|
||||
import rawDeepLearningClassifier.dlClassification.DLClassNameManager;
|
||||
import rawDeepLearningClassifier.dlClassification.DLClassiferModel;
|
||||
@ -39,7 +40,7 @@ import rawDeepLearningClassifier.layoutFX.DLModelSelectPane;
|
||||
import rawDeepLearningClassifier.layoutFX.DLSidePanelSwing;
|
||||
import rawDeepLearningClassifier.layoutFX.DLSymbolManager;
|
||||
import rawDeepLearningClassifier.layoutFX.PredictionSymbolManager;
|
||||
import rawDeepLearningClassifier.layoutFX.RawDLSettingsPane;
|
||||
import rawDeepLearningClassifier.layoutFX.DLSettingsPane;
|
||||
import rawDeepLearningClassifier.logging.DLAnnotationType;
|
||||
import rawDeepLearningClassifier.logging.DLDataUnitDatagram;
|
||||
import rawDeepLearningClassifier.logging.DLDetectionBinarySource;
|
||||
@ -124,7 +125,7 @@ public class DLControl extends PamControlledUnit implements PamSettings {
|
||||
/**
|
||||
* The settings pane.
|
||||
*/
|
||||
private RawDLSettingsPane settingsPane;
|
||||
private DLSettingsPane settingsPane;
|
||||
|
||||
/**
|
||||
* The settings dialog
|
||||
@ -188,10 +189,18 @@ public class DLControl extends PamControlledUnit implements PamSettings {
|
||||
*/
|
||||
private DLClassifierChooser dlClassifierChooser;
|
||||
|
||||
/**
|
||||
* Handles downloading models from the internet
|
||||
*/
|
||||
private DLDownloadManager modelDownloadManager;
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Handles downloading models from the internet
|
||||
*/
|
||||
private DLDefaultModelManager defaultModelManager;
|
||||
|
||||
|
||||
/**
|
||||
* Constructor for the DL Control.
|
||||
*
|
||||
@ -221,6 +230,9 @@ public class DLControl extends PamControlledUnit implements PamSettings {
|
||||
//manages the names assigned to different output classes.
|
||||
dlClassNameManager = new DLClassNameManager(this);
|
||||
|
||||
//manages default models
|
||||
defaultModelManager = new DLDefaultModelManager(this);
|
||||
|
||||
//manages downloading models
|
||||
modelDownloadManager = new DLDownloadManager();
|
||||
|
||||
@ -386,10 +398,10 @@ public class DLControl extends PamControlledUnit implements PamSettings {
|
||||
*
|
||||
* @return the settings pane.
|
||||
*/
|
||||
public RawDLSettingsPane getSettingsPane() {
|
||||
public DLSettingsPane getSettingsPane() {
|
||||
|
||||
if (this.settingsPane == null) {
|
||||
settingsPane = new RawDLSettingsPane(this);
|
||||
settingsPane = new DLSettingsPane(this);
|
||||
}
|
||||
|
||||
System.out.println("Get DL raw settings pane...");
|
||||
@ -591,6 +603,14 @@ public class DLControl extends PamControlledUnit implements PamSettings {
|
||||
return modelDownloadManager;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the default model manager. This handles the default models that can be downloaded.
|
||||
* @return the default model manager.
|
||||
*/
|
||||
public DLDefaultModelManager getDefaultModelManager() {
|
||||
return this.defaultModelManager;
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
@ -153,6 +153,8 @@ public class DLDownloadManager {
|
||||
|
||||
System.out.println("DOWNLOADED MODEL: " + file.getPath() );
|
||||
|
||||
notifyDownLoadListeners(DLStatus.DECOMPRESSING_MODEL, -1);
|
||||
|
||||
file = decompressFile(file);
|
||||
|
||||
if (file.isDirectory()) {
|
||||
@ -373,7 +375,7 @@ public class DLDownloadManager {
|
||||
Files.copy(input, outFile.toPath(), StandardCopyOption.REPLACE_EXISTING);
|
||||
|
||||
while ((n = input.read(buffer)) != -1) {
|
||||
// System.out.println("Chunk: " + n);
|
||||
System.out.println("Chunk: " + count);
|
||||
count=count+n; //total bytes
|
||||
notifyDownLoadListeners(DLStatus.DOWNLOADING, count);
|
||||
output.write( buffer, 0, n );
|
||||
@ -423,4 +425,9 @@ public class DLDownloadManager {
|
||||
URI path = dlDefaultModelManager.downloadModel(new RightWhaleModel1().getModelURI(), new RightWhaleModel1().getModelName());
|
||||
}
|
||||
|
||||
public void clearDownloadListeners() {
|
||||
this.downLoadListeners.clear();
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -1,33 +1,56 @@
|
||||
package rawDeepLearningClassifier;
|
||||
|
||||
/**
|
||||
* Status reporting for the deep learning module.
|
||||
* Status reporting for the deep learning module.
|
||||
*/
|
||||
public enum DLStatus {
|
||||
|
||||
FILE_NULL("The input file is null", "The loaded file was null. If the file was download it may not have downloaded properly.", true),
|
||||
FILE_NULL("The input file is null",
|
||||
"The loaded file was null. If the file was download it may not have downloaded properly.", ErrorLevel.ERROR),
|
||||
|
||||
MODEL_LOAD_FAILED("The model failed to load", " The model failed to load - this could be because it is incompatible with PAMGuard or an uknown file format.", true),
|
||||
MODEL_LOAD_FAILED("The model failed to load",
|
||||
" The model failed to load - this could be because it is incompatible with PAMGuard or an uknown file format.",
|
||||
ErrorLevel.ERROR),
|
||||
|
||||
MODEL_LOAD_SUCCESS("The model loaded", " The model successfully load", false),
|
||||
MODEL_LOAD_SUCCESS("The model loaded", " The model successfully load", ErrorLevel.NO_ERROR),
|
||||
|
||||
DOWNLOAD_STARTING("The model loaded", " The model successfully load", false),
|
||||
DOWNLOAD_STARTING("Download starting", "The model is downloading", ErrorLevel.NO_ERROR),
|
||||
|
||||
DOWNLOAD_FINISHED("The model loaded", " The model successfully load", false),
|
||||
DOWNLOAD_FINISHED("Download finished", " The model successfully downloaded", ErrorLevel.NO_ERROR),
|
||||
|
||||
DOWNLOADING("The model loaded", " The model successfully load", false),
|
||||
DOWNLOADING("Downloading", "The model is currently downloading", ErrorLevel.NO_ERROR),
|
||||
|
||||
NO_CONNECTION_TO_URL ("Could not connect to the URL", " Could connect to the URL - the URL may be wrong or there may be no internet connection", true),
|
||||
NO_CONNECTION_TO_URL("Could not connect to the URL",
|
||||
" Could connect to the URL - the URL may be wrong or there may be no internet connection", ErrorLevel.ERROR),
|
||||
|
||||
CONNECTION_TO_URL("The model loaded", " The model successfully load", false),
|
||||
CONNECTION_TO_URL("Connected to URL", "The connection to the URL was successful", ErrorLevel.NO_ERROR),
|
||||
|
||||
MODEL_DOWNLOAD_FAILED("The model was not downloaded", " The model download failed. Check internet connection and try again", true);
|
||||
MODEL_DOWNLOAD_FAILED("The model was not downloaded",
|
||||
" The model download failed. Check internet connection and try again", ErrorLevel.ERROR),
|
||||
|
||||
NO_MODEL_LOADED("There is no loaded model",
|
||||
"There is no loaded model. A model my have failed to load or the path/URL to the model is incorrect", ErrorLevel.WARNING),
|
||||
|
||||
//this is not a show stopper because predictions are saved there's just no binary classification.
|
||||
NO_BINARY_CLASSIFICATION("No binary classification",
|
||||
" There are no prediction classes selected for classification. Predicitons for each segment will be saved but there will be no detections generated",
|
||||
ErrorLevel.WARNING),
|
||||
|
||||
DECOMPRESSING_MODEL("Decompressing model", "Decompressing the model file", ErrorLevel.NO_ERROR), ;
|
||||
|
||||
|
||||
private boolean isError = true;
|
||||
/**
|
||||
* True of the message is an error message.
|
||||
*/
|
||||
private int isError = ErrorLevel.NO_ERROR;
|
||||
|
||||
/**
|
||||
* Check whether the message is an error message.
|
||||
*
|
||||
* @return true if an error message.
|
||||
*/
|
||||
public boolean isError() {
|
||||
return isError;
|
||||
return isError==ErrorLevel.ERROR;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -41,22 +64,54 @@ public enum DLStatus {
|
||||
private String expanded;
|
||||
|
||||
/**
|
||||
* Status report for the leep learning module.
|
||||
* @param string - status
|
||||
* @param expanded - description of the status.
|
||||
* Status report for the leep learning module.
|
||||
*
|
||||
* @param string - status
|
||||
* @param expanded - description of the status.
|
||||
*/
|
||||
DLStatus(String string, String expande, boolean isError) {
|
||||
DLStatus(String string, String expande, int isError) {
|
||||
this.string = string;
|
||||
this.expanded = expande;
|
||||
this.isError= isError;
|
||||
this.isError = isError;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get a brief description of the status.
|
||||
*
|
||||
* @return a brief description of the status.
|
||||
*/
|
||||
public String getName() {
|
||||
return string;
|
||||
}
|
||||
|
||||
/**
|
||||
* Longer description of the status.
|
||||
*
|
||||
* @return longer descrption of the status.
|
||||
*/
|
||||
public String getDescription() {
|
||||
return expanded;
|
||||
}
|
||||
|
||||
private static class ErrorLevel {
|
||||
public static final int NO_ERROR = 0;
|
||||
|
||||
public static final int WARNING = 1;
|
||||
|
||||
public static final int ERROR = 2;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the error flag. e.g. ErrorLevel.NO_ERROR. The error flag describes
|
||||
* whether the status is an error, warning or not an error.
|
||||
* @return the error flag.
|
||||
*/
|
||||
int getErrorFlag() {
|
||||
return isError;
|
||||
}
|
||||
|
||||
public boolean isWarning() {
|
||||
return isError==ErrorLevel.WARNING;
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -30,7 +30,6 @@ public class RawDLParams implements Serializable, Cloneable {
|
||||
/**
|
||||
* The current model URI. The deep learning model must have some sort of external file to run.
|
||||
* This might be a model, a .exe file etc.
|
||||
*
|
||||
*/
|
||||
public URI modelURI;
|
||||
|
||||
@ -86,7 +85,7 @@ public class RawDLParams implements Serializable, Cloneable {
|
||||
* different class names. If we change model then the class names may change.
|
||||
* Previously annotated data will then be messed up. But, in a giant dataset
|
||||
* that may be an issue. Perhaps users wish to run a new model on some chunk of
|
||||
* data without messing up all the other classified detection which have used
|
||||
* data without messing up all the other classified detectionS which have used
|
||||
* that module. So store the data in binary files? That is super inefficient as
|
||||
* the same string is stored many times. So instead store a short which
|
||||
* identifies the string that sits in this table. Everytime a new model is added
|
||||
|
@ -3,12 +3,14 @@ package rawDeepLearningClassifier.dataPlotFX;
|
||||
|
||||
import java.io.Serializable;
|
||||
|
||||
import PamController.PamController;
|
||||
import PamUtils.PamArrayUtils;
|
||||
import PamView.GeneralProjector;
|
||||
import PamView.GeneralProjector.ParameterType;
|
||||
import PamView.GeneralProjector.ParameterUnits;
|
||||
import PamView.symbol.PamSymbolChooser;
|
||||
import PamView.symbol.PamSymbolManager;
|
||||
import PamguardMVC.PamConstants;
|
||||
import PamguardMVC.PamDataBlock;
|
||||
import PamguardMVC.PamDataUnit;
|
||||
import dataPlotsFX.TDManagedSymbolChooserFX;
|
||||
@ -18,6 +20,7 @@ import dataPlotsFX.data.generic.GenericLinePlotInfo;
|
||||
import dataPlotsFX.data.generic.GenericScaleInfo;
|
||||
import dataPlotsFX.layout.TDGraphFX;
|
||||
import dataPlotsFX.projector.TDProjectorFX;
|
||||
import javafx.geometry.Point2D;
|
||||
import javafx.scene.canvas.GraphicsContext;
|
||||
import javafx.scene.paint.Color;
|
||||
import javafx.scene.shape.Polygon;
|
||||
@ -81,25 +84,31 @@ public class DLPredictionPlotInfoFX extends GenericLinePlotInfo {
|
||||
|
||||
frequencyInfo = new GenericScaleInfo(0, 1, ParameterType.FREQUENCY, ParameterUnits.HZ);
|
||||
|
||||
DLClassName[] classNames = getDlControl().getDLModel().getClassNames();
|
||||
updateClassNames();
|
||||
|
||||
System.out.println("Class names are: !!! " + (classNames == null ? "null" : classNames.length));
|
||||
|
||||
if (classNames!=null) {
|
||||
|
||||
//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);
|
||||
}
|
||||
|
||||
private void updateClassNames() {
|
||||
if (getDlControl().getDLModel()!=null) {
|
||||
DLClassName[] classNames = getDlControl().getDLModel().getClassNames();
|
||||
|
||||
System.out.println("Class names are: !!! " + (classNames == null ? "null" : classNames.length));
|
||||
|
||||
if (classNames!=null) {
|
||||
|
||||
//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)));
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
@ -334,5 +343,22 @@ public class DLPredictionPlotInfoFX extends GenericLinePlotInfo {
|
||||
|
||||
return dataD;
|
||||
}
|
||||
|
||||
/**
|
||||
* Notifications from the PamController are passed to this function.
|
||||
*
|
||||
* @param changeType - notification flag.
|
||||
*/
|
||||
public void notifyChange(int changeType) {
|
||||
super.notifyChange(changeType);
|
||||
|
||||
switch (changeType) {
|
||||
case PamController.CHANGED_PROCESS_SETTINGS:
|
||||
updateClassNames();
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -1,20 +1,6 @@
|
||||
package rawDeepLearningClassifier.defaultModels;
|
||||
|
||||
import java.io.File;
|
||||
import java.io.FileOutputStream;
|
||||
import java.io.IOException;
|
||||
import java.net.HttpURLConnection;
|
||||
import java.net.URI;
|
||||
import java.net.URL;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import PamUtils.FileFunctions;
|
||||
|
||||
import java.io.OutputStream;
|
||||
import java.io.InputStream;
|
||||
|
||||
import rawDeepLearningClassifier.DLControl;
|
||||
|
||||
/**
|
||||
@ -38,7 +24,11 @@ public class DLDefaultModelManager {
|
||||
*/
|
||||
public DLDefaultModelManager(DLControl dlControl) {
|
||||
this.dlControl = dlControl;
|
||||
defaultModels.add(new RightWhaleModel1());
|
||||
defaultModels.add(new HumpbackWhaleGoogle());
|
||||
defaultModels.add(new HumpbackWhaleAtlantic());
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Get a default model at index i
|
||||
@ -56,8 +46,5 @@ public class DLDefaultModelManager {
|
||||
public int getNumDefaultModels() {
|
||||
return defaultModels.size();
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
@ -1,5 +1,6 @@
|
||||
package rawDeepLearningClassifier.defaultModels;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.net.URI;
|
||||
|
||||
import rawDeepLearningClassifier.dlClassification.animalSpot.StandardModelParams;
|
||||
@ -32,11 +33,7 @@ public interface DLModel {
|
||||
* @return the model URI.
|
||||
*/
|
||||
public URI getModelURI();
|
||||
|
||||
/**
|
||||
* Get the model settings - these are used to ensure the model is set up correctly once loaded.
|
||||
*/
|
||||
public StandardModelParams getModelSettings();
|
||||
|
||||
|
||||
/**
|
||||
* The model name. This is used if, for example, a model is downloaded as a zip file and the model
|
||||
@ -44,6 +41,18 @@ public interface DLModel {
|
||||
* @return the model name;
|
||||
*/
|
||||
public String getModelName();
|
||||
|
||||
/**
|
||||
* Get the link to the paper for the model
|
||||
* @return the citation link.
|
||||
*/
|
||||
public URI getCitationLink();
|
||||
|
||||
/**
|
||||
* Set the model settings once it has loaded.
|
||||
* @param dlModelSettings - the model settings.
|
||||
*/
|
||||
public void setParams(Serializable dlModelSettings);
|
||||
|
||||
|
||||
|
||||
|
@ -0,0 +1,66 @@
|
||||
package rawDeepLearningClassifier.defaultModels;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.net.MalformedURLException;
|
||||
import java.net.URI;
|
||||
import java.net.URISyntaxException;
|
||||
import java.net.URL;
|
||||
|
||||
import rawDeepLearningClassifier.dlClassification.animalSpot.StandardModelParams;
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
public class HumpbackWhaleAtlantic implements DLModel {
|
||||
|
||||
@Override
|
||||
public String getDescription() {
|
||||
return "Detects Atlantic Humpback whales";
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getName() {
|
||||
return "Humpback Whale Atlantic";
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getCitation() {
|
||||
return "A. N. Allen et al., ‘A Convolutional Neural Network for Automated Detection of Humpback Whale Song in a Diverse, Long-Term Passive Acoustic Dataset’, Front. Mar. Sci., vol. 8, p. 607321, Mar. 2021";
|
||||
}
|
||||
|
||||
@Override
|
||||
public URI getModelURI() {
|
||||
try {
|
||||
return new URL("https://github.com/PAMGuard/deeplearningmodels/raw/master/right_whale_1/model_lenet_dropout_input_conv_all.zip").toURI();
|
||||
} catch (MalformedURLException | URISyntaxException e) {
|
||||
// TODO Auto-generated catch block
|
||||
e.printStackTrace();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getModelName() {
|
||||
return "saved_model.pb";
|
||||
}
|
||||
|
||||
@Override
|
||||
public URI getCitationLink() {
|
||||
try {
|
||||
return new URL("https://doi.org/10.3389/fmars.2021.607321").toURI();
|
||||
} catch (MalformedURLException | URISyntaxException e) {
|
||||
// TODO Auto-generated catch block
|
||||
e.printStackTrace();
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setParams(Serializable dlModelSettings) {
|
||||
// TODO Auto-generated method stub
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
@ -0,0 +1,96 @@
|
||||
package rawDeepLearningClassifier.defaultModels;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.net.MalformedURLException;
|
||||
import java.net.URI;
|
||||
import java.net.URISyntaxException;
|
||||
import java.net.URL;
|
||||
import java.util.ArrayList;
|
||||
|
||||
import org.jamdev.jdl4pam.transforms.DLTransformsFactory;
|
||||
import org.jamdev.jdl4pam.transforms.DLTransfromParams;
|
||||
import org.jamdev.jdl4pam.transforms.SimpleTransformParams;
|
||||
import org.jamdev.jdl4pam.transforms.DLTransform.DLTransformType;
|
||||
|
||||
import rawDeepLearningClassifier.dlClassification.DLClassName;
|
||||
import rawDeepLearningClassifier.dlClassification.genericModel.GenericModelParams;
|
||||
import rawDeepLearningClassifier.layoutFX.exampleSounds.ExampleSoundFactory.ExampleSoundType;
|
||||
|
||||
public class HumpbackWhaleGoogle implements DLModel {
|
||||
|
||||
@Override
|
||||
public String getDescription() {
|
||||
return "A model developed by Google to detect Humpback whales (Megaptera novaeangliae) in the Pacific ocean";
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getName() {
|
||||
return "Humpback Whale Pacific";
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getCitation() {
|
||||
return "A. N. Allen et al., ‘A Convolutional Neural Network for Automated Detection of Humpback Whale Song in a Diverse, Long-Term Passive Acoustic Dataset’, Front. Mar. Sci., vol. 8, p. 607321, Mar. 2021";
|
||||
}
|
||||
|
||||
@Override
|
||||
public URI getModelURI() {
|
||||
try {
|
||||
return new URL("https://github.com/PAMGuard/deeplearningmodels/raw/master/humpback_whale_1/humpback_whale_1.zip").toURI();
|
||||
} catch (MalformedURLException | URISyntaxException e) {
|
||||
// TODO Auto-generated catch block
|
||||
e.printStackTrace();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getModelName() {
|
||||
return "saved_model.pb";
|
||||
}
|
||||
|
||||
@Override
|
||||
public URI getCitationLink() {
|
||||
try {
|
||||
return new URL("https://doi.org/10.3389/fmars.2021.607321").toURI();
|
||||
} catch (MalformedURLException | URISyntaxException e) {
|
||||
// TODO Auto-generated catch block
|
||||
e.printStackTrace();
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setParams(Serializable dlModelSettings) {
|
||||
GenericModelParams genericModelParams = (GenericModelParams) dlModelSettings;
|
||||
|
||||
//decimation value
|
||||
float sr = 10000;
|
||||
|
||||
//create the transforms.
|
||||
ArrayList<DLTransfromParams> dlTransformParamsArr = new ArrayList<DLTransfromParams>();
|
||||
|
||||
dlTransformParamsArr.add(new SimpleTransformParams(DLTransformType.DECIMATE, sr));
|
||||
|
||||
genericModelParams.dlTransfromParams = dlTransformParamsArr;
|
||||
|
||||
genericModelParams.defaultSegmentLen = 3.92*1000;
|
||||
genericModelParams.binaryClassification = new boolean[] {true};
|
||||
genericModelParams.classNames= new DLClassName[] {new DLClassName("Humpback whale", (short) 1)};
|
||||
genericModelParams.numClasses = 1;
|
||||
|
||||
|
||||
genericModelParams.defaultShape= new Long[] {-1L,-1L,-1L,1L};
|
||||
genericModelParams.shape= new Long[] {-1L,-1L,-1L,1L};
|
||||
|
||||
//create the transforms.
|
||||
genericModelParams.dlTransfroms = DLTransformsFactory.makeDLTransforms((ArrayList<DLTransfromParams>)genericModelParams.dlTransfromParams);
|
||||
|
||||
genericModelParams.setExampleSound(ExampleSoundType.HUMPBACK_WHALE);
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
@ -1,11 +1,21 @@
|
||||
package rawDeepLearningClassifier.defaultModels;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.net.MalformedURLException;
|
||||
import java.net.URI;
|
||||
import java.net.URISyntaxException;
|
||||
import java.net.URL;
|
||||
import java.util.ArrayList;
|
||||
|
||||
import org.jamdev.jdl4pam.transforms.DLTransform.DLTransformType;
|
||||
import org.jamdev.jdl4pam.transforms.DLTransformsFactory;
|
||||
import org.jamdev.jdl4pam.transforms.DLTransfromParams;
|
||||
import org.jamdev.jdl4pam.transforms.SimpleTransformParams;
|
||||
|
||||
import rawDeepLearningClassifier.dlClassification.DLClassName;
|
||||
import rawDeepLearningClassifier.dlClassification.animalSpot.StandardModelParams;
|
||||
import rawDeepLearningClassifier.dlClassification.genericModel.GenericModelParams;
|
||||
import rawDeepLearningClassifier.layoutFX.exampleSounds.ExampleSoundFactory.ExampleSoundType;
|
||||
|
||||
/**
|
||||
* Right whale model from Shiu et al. 2019
|
||||
@ -18,18 +28,17 @@ public class RightWhaleModel1 implements DLModel {
|
||||
|
||||
@Override
|
||||
public String getDescription() {
|
||||
return "Detects right whales";
|
||||
return "Detects North Atlantic right whales (Eubalaena glacialis).";
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getName() {
|
||||
return "Right Whale";
|
||||
return "North Atlantic right whale";
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getCitation() {
|
||||
return " Shiu, Y., Palmer, K.J., Roch, M.A., Fleishman, E., Liu, X., Nosal, E.-M., Helble, T., Cholewiak, D., Gillespie, D., Klinck, H., 2020."
|
||||
+ " Deep neural networks for automated detection of marine mammal species. Scientific Reports 10, 607. https://doi.org/10.1038/s41598-020-57549-y";
|
||||
return "Shiu, Y., Palmer, K.J., Roch, M.A. et al. Deep neural networks for automated detection of marine mammal species. Sci Rep 10, 607 (2020)";
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -44,15 +53,62 @@ public class RightWhaleModel1 implements DLModel {
|
||||
}
|
||||
|
||||
@Override
|
||||
public StandardModelParams getModelSettings() {
|
||||
// TODO Auto-generated method stub
|
||||
return null;
|
||||
/**
|
||||
* Set the model settings once it has loaded.
|
||||
* @param dlModelSettings - the model settings.
|
||||
*/
|
||||
public void setParams(Serializable dlModelSettings) {
|
||||
|
||||
GenericModelParams genericModelParams = (GenericModelParams) dlModelSettings;
|
||||
|
||||
//decimation value
|
||||
float sr = 2000;
|
||||
|
||||
//create the transforms.
|
||||
ArrayList<DLTransfromParams> dlTransformParamsArr = new ArrayList<DLTransfromParams>();
|
||||
|
||||
dlTransformParamsArr.add(new SimpleTransformParams(DLTransformType.DECIMATE, sr));
|
||||
// dlTransformParamsArr.add(new SimpleTransformParams(DLTransformType.PREEMPHSIS, preemphases));
|
||||
dlTransformParamsArr.add(new SimpleTransformParams(DLTransformType.SPECTROGRAM, 256, 102));
|
||||
//in the python code they have an sfft of 129xN where N is the number of chunks. They then
|
||||
//choose fft data between bin 5 and 45 in the FFT. This roughly between 40 and 350 Hz.
|
||||
dlTransformParamsArr.add(new SimpleTransformParams(DLTransformType.SPECCROPINTERP, 47.0, 357.0, 40));
|
||||
dlTransformParamsArr.add(new SimpleTransformParams(DLTransformType.SPECNORMALISEROWSUM));
|
||||
|
||||
|
||||
genericModelParams.dlTransfromParams = dlTransformParamsArr;
|
||||
|
||||
genericModelParams.defaultSegmentLen = 2.0*1000;
|
||||
genericModelParams.binaryClassification = new boolean[] {false, true};
|
||||
|
||||
genericModelParams.defaultShape= new Long[] {-1L,40l,401L,1L};
|
||||
genericModelParams.shape= new Long[] {-1L,40L,40L,1L};
|
||||
|
||||
genericModelParams.classNames= new DLClassName[] {new DLClassName("Noise", (short) 0), new DLClassName("Right Whale", (short) 1)};
|
||||
genericModelParams.numClasses = 2;
|
||||
|
||||
//create the transforms.
|
||||
genericModelParams.dlTransfroms = DLTransformsFactory.makeDLTransforms((ArrayList<DLTransfromParams>)genericModelParams.dlTransfromParams);
|
||||
|
||||
genericModelParams.setExampleSound(ExampleSoundType.RIGHT_WHALE);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getModelName() {
|
||||
return "saved_model.pb";
|
||||
}
|
||||
|
||||
@Override
|
||||
public URI getCitationLink() {
|
||||
try {
|
||||
return new URL("https://doi.org/10.1038/s41598-020-57549-y").toURI();
|
||||
} catch (MalformedURLException | URISyntaxException e) {
|
||||
// TODO Auto-generated catch block
|
||||
e.printStackTrace();
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
@ -10,6 +10,7 @@ import org.jamdev.jdl4pam.transforms.SimpleTransform;
|
||||
import org.jamdev.jdl4pam.transforms.SimpleTransformParams;
|
||||
|
||||
import rawDeepLearningClassifier.DLControl;
|
||||
import rawDeepLearningClassifier.DLStatus;
|
||||
import rawDeepLearningClassifier.layoutFX.DLCLassiferModelUI;
|
||||
import rawDeepLearningClassifier.segmenter.SegmenterProcess.GroupedRawData;
|
||||
import warnings.PamWarning;
|
||||
@ -100,14 +101,14 @@ public interface DLClassiferModel {
|
||||
/**
|
||||
* Check whether a model has been selected and can be loaded successfully.
|
||||
*/
|
||||
public boolean checkModelOK();
|
||||
public DLStatus getModelStatus();
|
||||
|
||||
/**
|
||||
* Get warnings for the classifier model. This is called when the user confirms settings and
|
||||
* used to return a warning dialog.
|
||||
* @return a list of warnings. If the list is null or size() is zero then settings are OK.
|
||||
*/
|
||||
public ArrayList<PamWarning> checkSettingsOK();
|
||||
// /**
|
||||
// * Get warnings for the classifier model. This is called when the user confirms settings and
|
||||
// * used to return a warning dialog.
|
||||
// * @return a list of warnings. If the list is null or size() is zero then settings are OK.
|
||||
// */
|
||||
// public ArrayList<PamWarning> checkSettingsOK();
|
||||
|
||||
|
||||
/**
|
||||
|
@ -14,11 +14,12 @@ import PamUtils.PamArrayUtils;
|
||||
import PamUtils.PamCalendar;
|
||||
import javafx.stage.FileChooser.ExtensionFilter;
|
||||
import rawDeepLearningClassifier.DLControl;
|
||||
import rawDeepLearningClassifier.DLStatus;
|
||||
import rawDeepLearningClassifier.dlClassification.animalSpot.StandardModelParams;
|
||||
import rawDeepLearningClassifier.dlClassification.genericModel.DLModelWorker;
|
||||
import rawDeepLearningClassifier.dlClassification.genericModel.GenericDLClassifier;
|
||||
import rawDeepLearningClassifier.dlClassification.genericModel.GenericPrediction;
|
||||
import rawDeepLearningClassifier.layoutFX.RawDLSettingsPane;
|
||||
import rawDeepLearningClassifier.layoutFX.DLSettingsPane;
|
||||
import rawDeepLearningClassifier.segmenter.SegmenterProcess.GroupedRawData;
|
||||
import warnings.PamWarning;
|
||||
import warnings.WarningSystem;
|
||||
@ -153,8 +154,30 @@ public abstract class StandardClassifierModel implements DLClassiferModel, PamSe
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean checkModelOK() {
|
||||
return !getDLWorker().isModelNull();
|
||||
public DLStatus getModelStatus() {
|
||||
if (getDLWorker().isModelNull()) {
|
||||
return DLStatus.MODEL_LOAD_FAILED;
|
||||
}
|
||||
|
||||
File file = new File(getDLParams().modelPath);
|
||||
if (getDLParams().modelPath == null || !file.isFile()) {
|
||||
return DLStatus.NO_MODEL_LOADED;
|
||||
}
|
||||
|
||||
// if continous data is selected and all classes are false then this is a
|
||||
// potential mistake...
|
||||
if (dlControl.getSettingsPane().getSelectedParentDataBlock().getUnitClass() == RawDataUnit.class
|
||||
&& (getDLParams().binaryClassification==null || PamArrayUtils.isAllFalse(getDLParams().binaryClassification))){
|
||||
return DLStatus.NO_BINARY_CLASSIFICATION;
|
||||
// warnings.add(new PamWarning("Generic classifier",
|
||||
// "There are no prediction classes selected for classification. "
|
||||
// + "Predicitons for each segment will be saved but there will be no detections generated",
|
||||
// 1));
|
||||
}
|
||||
|
||||
|
||||
|
||||
return DLStatus.MODEL_LOAD_SUCCESS;
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -201,11 +224,11 @@ public abstract class StandardClassifierModel implements DLClassiferModel, PamSe
|
||||
protected void newResult(GenericPrediction modelResult, GroupedRawData groupedRawData) {
|
||||
this.dlControl.getDLClassifyProcess().newModelResult(modelResult, groupedRawData);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ArrayList<PamWarning> checkSettingsOK() {
|
||||
return checkSettingsOK(getDLParams(), dlControl);
|
||||
}
|
||||
//
|
||||
// @Override
|
||||
// public ArrayList<PamWarning> checkSettingsOK() {
|
||||
// return checkSettingsOK(getDLParams(), dlControl);
|
||||
// }
|
||||
|
||||
|
||||
/**
|
||||
@ -221,7 +244,7 @@ public abstract class StandardClassifierModel implements DLClassiferModel, PamSe
|
||||
* Get raw settings pane
|
||||
* @return the setting pane.
|
||||
*/
|
||||
public RawDLSettingsPane getRawSettingsPane() {
|
||||
public DLSettingsPane getRawSettingsPane() {
|
||||
return this.dlControl.getSettingsPane();
|
||||
}
|
||||
|
||||
|
@ -327,13 +327,18 @@ public abstract class StandardModelPane extends SettingsPane<StandardModelParams
|
||||
|
||||
@Override
|
||||
public void setParams(StandardModelParams currParams) {
|
||||
this.paramsClone = currParams.clone();
|
||||
try {
|
||||
|
||||
this.paramsClone = currParams.clone();
|
||||
|
||||
//pathLabel .setText(this.currentSelectedFile.getPath());
|
||||
|
||||
detectionSpinner.getValueFactory().setValue(Double.valueOf(currParams.threshold));
|
||||
|
||||
|
||||
//set the params on the advanced pane.
|
||||
// System.out.println("SET PARAMS ADV PANE: " + (paramsClone.classNames == null ? null : paramsClone.classNames.length));
|
||||
|
||||
this.getAdvSettingsPane().setParams(paramsClone);
|
||||
//System.out.println("SET advanced params: " + paramsClone.dlTransfroms);
|
||||
|
||||
@ -346,6 +351,12 @@ public abstract class StandardModelPane extends SettingsPane<StandardModelParams
|
||||
|
||||
usedefaultSeg.setSelected(currParams.useDefaultSegLen);
|
||||
defaultSegmentLenChanged();
|
||||
|
||||
}
|
||||
|
||||
catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
//updatePathLabel();
|
||||
|
||||
|
@ -10,6 +10,7 @@ import org.jamdev.jdl4pam.transforms.DLTransform;
|
||||
import org.jamdev.jdl4pam.transforms.DLTransfromParams;
|
||||
|
||||
import rawDeepLearningClassifier.dlClassification.DLClassName;
|
||||
import rawDeepLearningClassifier.layoutFX.exampleSounds.ExampleSoundFactory.ExampleSoundType;
|
||||
|
||||
/**
|
||||
* Parameters for the SoundSpot model.
|
||||
@ -101,6 +102,21 @@ public class StandardModelParams implements Serializable, Cloneable {
|
||||
public int exampleSoundIndex = 0;
|
||||
|
||||
|
||||
/**
|
||||
* Set the example sound that should be associated with parameters.
|
||||
* @param soundType - the example sound type.
|
||||
*/
|
||||
public void setExampleSound(ExampleSoundType soundType) {
|
||||
ExampleSoundType[] values = ExampleSoundType.values();
|
||||
for (int i=0; i<values.length; i++) {
|
||||
if (values[i].equals(soundType)) {
|
||||
exampleSoundIndex = i;
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Set the URI in standard model params.
|
||||
* @param uri - the uri to a model
|
||||
|
@ -5,6 +5,7 @@ import java.net.URI;
|
||||
import java.util.ArrayList;
|
||||
|
||||
import rawDeepLearningClassifier.DLControl;
|
||||
import rawDeepLearningClassifier.DLStatus;
|
||||
import rawDeepLearningClassifier.dlClassification.DLClassName;
|
||||
import rawDeepLearningClassifier.dlClassification.DLClassiferModel;
|
||||
import rawDeepLearningClassifier.dlClassification.PredictionResult;
|
||||
@ -80,16 +81,12 @@ public class DummyClassifier implements DLClassiferModel{
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean checkModelOK() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ArrayList<PamWarning> checkSettingsOK() {
|
||||
// TODO Auto-generated method stub
|
||||
public DLStatus getModelStatus() {
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
|
||||
@Override
|
||||
public boolean isModelType(URI uri) {
|
||||
// TODO Auto-generated method stub
|
||||
|
@ -418,7 +418,7 @@ public class GenericAdvPane extends SettingsPane<GenericModelParams> {
|
||||
|
||||
@Override
|
||||
public void setParams(GenericModelParams input) {
|
||||
|
||||
|
||||
setParams= true;
|
||||
|
||||
this.currentInput = input.clone();
|
||||
|
@ -180,16 +180,6 @@ public class GenericDLClassifier extends StandardClassifierModel {
|
||||
this.genericModelParams=(GenericModelParams) clone;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
@Override
|
||||
public boolean checkModelOK() {
|
||||
return genericModelWorker.getModel()!=null;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Send a new result form the thread queue to the process.
|
||||
* @param modelResult - the model result;
|
||||
@ -230,10 +220,10 @@ public class GenericDLClassifier extends StandardClassifierModel {
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public ArrayList<PamWarning> checkSettingsOK() {
|
||||
return checkSettingsOK(genericModelParams, dlControl);
|
||||
}
|
||||
// @Override
|
||||
// public ArrayList<PamWarning> checkSettingsOK() {
|
||||
// return checkSettingsOK(genericModelParams, dlControl);
|
||||
// }
|
||||
|
||||
|
||||
|
||||
|
@ -76,9 +76,7 @@ public class GenericImportExportPane extends ImportExportPane {
|
||||
|
||||
//set the default segment length if available.
|
||||
if (genericModelParams.defaultSegmentLen!=null) {
|
||||
double sR = genericAdvPane.getDLControl().getSettingsPane().getSelectedParentDataBlock().getSampleRate();
|
||||
//automatically set the default segment length.
|
||||
genericAdvPane.getDLControl().getSettingsPane().getSegmentLenSpinner().getValueFactory().setValue((int) (sR*genericModelParams.defaultSegmentLen/1000.));
|
||||
genericAdvPane.getDLControl().getSettingsPane().setSegmentLength(genericModelParams.defaultSegmentLen);
|
||||
}
|
||||
|
||||
if (genericModelParams==null) {
|
||||
|
@ -71,6 +71,8 @@ public class GenericModelPane extends StandardModelPane {
|
||||
|
||||
@Override
|
||||
public void setParams(StandardModelParams currParams) {
|
||||
// System.out.println("SET PARAMS GENERIC PANE: " + currParams);
|
||||
|
||||
super.setParams(currParams);
|
||||
}
|
||||
|
||||
|
@ -6,6 +6,7 @@ import org.jamdev.jdl4pam.transforms.DLTransform.DLTransformType;
|
||||
import org.json.JSONArray;
|
||||
|
||||
import rawDeepLearningClassifier.dlClassification.animalSpot.StandardModelParams;
|
||||
import rawDeepLearningClassifier.layoutFX.exampleSounds.ExampleSoundFactory.ExampleSoundType;
|
||||
|
||||
import org.jamdev.jdl4pam.transforms.DLTransformsFactory;
|
||||
import org.jamdev.jdl4pam.transforms.DLTransfromParams;
|
||||
@ -186,4 +187,6 @@ public class GenericModelParams extends StandardModelParams implements Cloneable
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
@ -72,7 +72,7 @@ public class GenericModelUI implements DLCLassiferModelUI {
|
||||
|
||||
@Override
|
||||
public void setParams() {
|
||||
// System.out.println("Set model params: " + genericModelClassifier.getGenericDLParams().dlTransfromParams.size());
|
||||
// System.out.println("SE MODEL UI PARAMS: " + genericModelClassifier.getGenericDLParams().dlTransfromParams.size());
|
||||
getSettingsPane().setParams(genericModelClassifier.getGenericDLParams());
|
||||
}
|
||||
|
||||
|
@ -45,7 +45,7 @@ public class GenericModelWorker extends DLModelWorker<GenericPrediction> {
|
||||
}
|
||||
results = genericModel.runModel(waveStack);
|
||||
}
|
||||
//System.out.println("GENERIC MODEL RESULTS: " + results== null ? null : results.length);
|
||||
System.out.println("GENERIC MODEL RESULTS: " + results== null ? null : results.length);
|
||||
return results;
|
||||
}
|
||||
|
||||
|
@ -179,6 +179,7 @@ public class KetosWorker extends DLModelWorker<GenericPrediction> {
|
||||
|
||||
@Override
|
||||
public float[] runModel(float[][][] transformedDataStack) {
|
||||
System.out.println("Model input: " + transformedDataStack.length + " " + transformedDataStack[0].length + " " + transformedDataStack[0][0].length);
|
||||
return ketosModel.runModel(transformedDataStack);
|
||||
}
|
||||
|
||||
|
@ -11,6 +11,7 @@ import PamController.PamControlledUnitSettings;
|
||||
import PamController.PamSettingManager;
|
||||
import PamController.PamSettings;
|
||||
import rawDeepLearningClassifier.DLControl;
|
||||
import rawDeepLearningClassifier.DLStatus;
|
||||
import rawDeepLearningClassifier.dlClassification.DLClassName;
|
||||
import rawDeepLearningClassifier.dlClassification.DLClassiferModel;
|
||||
import rawDeepLearningClassifier.dlClassification.DLDataUnit;
|
||||
@ -340,16 +341,16 @@ public class OrcaSpotClassifier implements DLClassiferModel, PamSettings {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean checkModelOK() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ArrayList<PamWarning> checkSettingsOK() {
|
||||
// TODO Auto-generated method stub
|
||||
public DLStatus getModelStatus() {
|
||||
return null;
|
||||
}
|
||||
|
||||
// @Override
|
||||
// public ArrayList<PamWarning> checkSettingsOK() {
|
||||
// // TODO Auto-generated method stub
|
||||
// return null;
|
||||
// }
|
||||
|
||||
@Override
|
||||
public boolean isModelType(URI uri) {
|
||||
// TODO Auto-generated method stub
|
||||
|
@ -13,14 +13,15 @@ import org.controlsfx.control.PopOver;
|
||||
import ai.djl.Device;
|
||||
import javafx.concurrent.Task;
|
||||
import javafx.geometry.Pos;
|
||||
import javafx.scene.Node;
|
||||
import javafx.scene.control.Label;
|
||||
import javafx.scene.control.ProgressIndicator;
|
||||
import javafx.scene.control.TextField;
|
||||
import javafx.scene.control.Tooltip;
|
||||
import javafx.scene.control.MenuButton;
|
||||
import javafx.scene.control.MenuItem;
|
||||
|
||||
import javafx.scene.layout.Pane;
|
||||
import javafx.scene.layout.Priority;
|
||||
import javafx.scene.paint.Color;
|
||||
import javafx.scene.text.Font;
|
||||
import javafx.scene.text.FontWeight;
|
||||
import javafx.stage.FileChooser;
|
||||
@ -38,7 +39,8 @@ import rawDeepLearningClassifier.DLControl;
|
||||
import rawDeepLearningClassifier.DLStatus;
|
||||
import rawDeepLearningClassifier.dlClassification.DLClassiferModel;
|
||||
import rawDeepLearningClassifier.dlClassification.DefaultModels;
|
||||
import rawDeepLearningClassifier.dlClassification.DefaultModels.DefualtModel;
|
||||
import rawDeepLearningClassifier.dlClassification.animalSpot.StandardModelParams;
|
||||
import rawDeepLearningClassifier.layoutFX.defaultModels.DefaultModelPane;
|
||||
|
||||
|
||||
/**
|
||||
@ -103,10 +105,12 @@ public class DLModelSelectPane extends PamBorderPane {
|
||||
|
||||
private TextField uriTextField;
|
||||
|
||||
private RawDLSettingsPane rawDLSettingsPane;
|
||||
private DLSettingsPane rawDLSettingsPane;
|
||||
|
||||
private DefaultModelPane defaultModelPane;
|
||||
|
||||
|
||||
public DLModelSelectPane(RawDLSettingsPane rawDLSettingsPane) {
|
||||
public DLModelSelectPane(DLSettingsPane rawDLSettingsPane) {
|
||||
this.rawDLSettingsPane=rawDLSettingsPane;
|
||||
this.dlControl=rawDLSettingsPane.getDLControl();
|
||||
this.setCenter(createDLSelectPane());
|
||||
@ -118,8 +122,6 @@ public class DLModelSelectPane extends PamBorderPane {
|
||||
|
||||
public Pane createDLSelectPane() {
|
||||
|
||||
defaultModels = new DefaultModels(dlControl);
|
||||
|
||||
|
||||
classiferInfoLabel = new Label(" Classifier");
|
||||
//PamGuiManagerFX.titleFont2style(classiferInfoLabel);
|
||||
@ -130,13 +132,14 @@ public class DLModelSelectPane extends PamBorderPane {
|
||||
pathLabel = new Label("No classifier file selected");
|
||||
// PamButton pamButton = new PamButton("", PamGlyphDude.createPamGlyph(MaterialDesignIcon.FILE, PamGuiManagerFX.iconSize));
|
||||
PamButton pamButton = new PamButton("", PamGlyphDude.createPamIcon("mdi2f-file", PamGuiManagerFX.iconSize));
|
||||
pathLabel.setPrefWidth(100);
|
||||
|
||||
modelLoadIndicator = new ProgressIndicator(-1);
|
||||
modelLoadIndicator.setVisible(false);
|
||||
modelLoadIndicator.prefHeightProperty().bind(pamButton.heightProperty().subtract(3));
|
||||
|
||||
pamButton.setMinWidth(30);
|
||||
pamButton.setTooltip(new Tooltip("Browse to select a model file"));
|
||||
pamButton.setTooltip(new Tooltip("Load a model from a file"));
|
||||
|
||||
|
||||
pamButton.setOnAction((action)->{
|
||||
@ -220,16 +223,59 @@ public class DLModelSelectPane extends PamBorderPane {
|
||||
});
|
||||
|
||||
|
||||
MenuButton defaults = new MenuButton();
|
||||
PamButton defaults = new PamButton();
|
||||
defaults.setTooltip(new Tooltip("Default models"));
|
||||
defaults.setGraphic(PamGlyphDude.createPamIcon("mdi2d-dots-vertical", PamGuiManagerFX.iconSize));
|
||||
defaults.setTooltip(new Tooltip("Load a default model"));
|
||||
|
||||
for (DefualtModel defaultmodel: defaultModels.getDefaultModels()) {
|
||||
defaults.getItems().add(new MenuItem(defaultmodel.name));
|
||||
}
|
||||
defaults.prefHeightProperty().bind(urlButton.heightProperty());
|
||||
|
||||
// for (DefualtModel defaultmodel: defaultModels.getDefaultModels()) {
|
||||
// defaults.getItems().add(new MenuItem(defaultmodel.name));
|
||||
// }
|
||||
// defaults.prefHeightProperty().bind(urlButton.heightProperty());
|
||||
|
||||
defaultModelPane = new DefaultModelPane(this.dlControl.getDefaultModelManager());
|
||||
defaultModelPane.setPadding(new Insets(5,5,5,5));
|
||||
defaultModelPane.defaultModelProperty().addListener((obsVal, oldVal, newVal)->{
|
||||
if (newVal!=oldVal) {
|
||||
//a default model needs to be loaded.
|
||||
Task<DLStatus> task = loadNewModel(newVal.getModelURI());
|
||||
|
||||
task.setOnSucceeded((val)->{
|
||||
if (currentClassifierModel!=null) {
|
||||
|
||||
//set the parameters from the classifer model to have correct
|
||||
//transfroms etc.
|
||||
newVal.setParams(currentClassifierModel.getDLModelSettings());
|
||||
|
||||
//set the correct classifier pane.
|
||||
rawDLSettingsPane.setClassifierPane();
|
||||
|
||||
//need to make sure the classifier pane is updated
|
||||
currentClassifierModel.getModelUI().setParams();
|
||||
|
||||
//need to update the segment length...
|
||||
if (currentClassifierModel.getDLModelSettings() instanceof StandardModelParams) {
|
||||
double segLen = ((StandardModelParams) currentClassifierModel.getDLModelSettings()).defaultSegmentLen;
|
||||
this.rawDLSettingsPane.setSegmentLength(segLen);
|
||||
//set to half the hop size too
|
||||
this.rawDLSettingsPane.setHopLength(segLen/2);
|
||||
}
|
||||
|
||||
}
|
||||
else {
|
||||
//this should never happen unless there is no internet
|
||||
System.err.println("Default model failed ot load: "+ newVal);
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
PopOver defualtModelPopOver = new PopOver();
|
||||
defualtModelPopOver.setContentNode(defaultModelPane);
|
||||
|
||||
defaults.setOnAction((action)->{
|
||||
defualtModelPopOver.show(defaults);
|
||||
});
|
||||
|
||||
PamHBox hBox = new PamHBox();
|
||||
hBox.setSpacing(5);
|
||||
@ -244,21 +290,21 @@ public class DLModelSelectPane extends PamBorderPane {
|
||||
* Load a new model on a seperate thread.
|
||||
* @param uri - the uri to the model.
|
||||
*/
|
||||
public void loadNewModel(URI uri) {
|
||||
public Task<DLStatus> loadNewModel(URI uri) {
|
||||
// separate non-FX thread - load the model
|
||||
//on a separate thread so we can show a moving load
|
||||
//bar on the FX thread. Otherwise the GUI locks up
|
||||
//whilst stuff is loaded.
|
||||
if (uri==null) return;
|
||||
if (uri==null) return null;
|
||||
|
||||
// pathLabel.setText("Loading model...");
|
||||
modelLoadIndicator.setVisible(true);
|
||||
|
||||
|
||||
|
||||
Task<DLStatus> task = new LoadTask(uri);
|
||||
|
||||
|
||||
modelLoadIndicator.progressProperty().bind(task.progressProperty());
|
||||
|
||||
pathLabel.setGraphic(null); //remove error icon if there is one.
|
||||
pathLabel.textProperty().bind(task.messageProperty());
|
||||
|
||||
|
||||
@ -266,6 +312,8 @@ public class DLModelSelectPane extends PamBorderPane {
|
||||
Thread th = new Thread(task);
|
||||
th.setDaemon(true);
|
||||
th.start();
|
||||
|
||||
return task;
|
||||
|
||||
|
||||
|
||||
@ -310,7 +358,7 @@ public class DLModelSelectPane extends PamBorderPane {
|
||||
|
||||
/**
|
||||
* A new model has been selected
|
||||
* @param
|
||||
* @param the load status of the model.
|
||||
*/
|
||||
private DLStatus newModelSelected(URI file) {
|
||||
|
||||
@ -328,7 +376,8 @@ public class DLModelSelectPane extends PamBorderPane {
|
||||
//we are loading model from a file - anything can happen so put in a try catch.
|
||||
currentClassifierModel.setModel(file);
|
||||
|
||||
if (!currentClassifierModel.checkModelOK()) {
|
||||
if (currentClassifierModel.getModelStatus().isError()) {
|
||||
System.err.println("Model load failed: " + currentClassifierModel.getModelStatus());
|
||||
currentClassifierModel=null;
|
||||
return DLStatus.MODEL_LOAD_FAILED;
|
||||
}
|
||||
@ -348,36 +397,73 @@ public class DLModelSelectPane extends PamBorderPane {
|
||||
}
|
||||
|
||||
private void showWarningDialog(DLStatus status) {
|
||||
PamDialogFX.showError(status.getName(), status.getDescription());
|
||||
this.rawDLSettingsPane.showWarning(status);
|
||||
// PamDialogFX.showError(status.getName(), status.getDescription());
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Create an error icon based on the status message.
|
||||
* @param status - the status
|
||||
* @return error icon or null of the status is not an error.
|
||||
*/
|
||||
private Node createErrorIcon(DLStatus status) {
|
||||
Node decoration = null;
|
||||
if (status.isError()){
|
||||
decoration = PamGlyphDude.createPamIcon("mdi2c-close-circle-outline", Color.RED, 10);
|
||||
}
|
||||
else if (status.isWarning()) {
|
||||
decoration = PamGlyphDude.createPamIcon("mdi2c-close-circle-outline", Color.ORANGE, 10);
|
||||
}
|
||||
return decoration;
|
||||
}
|
||||
|
||||
/**
|
||||
* Update the path label and tool tip text;
|
||||
* Update the path label and tool tip text
|
||||
*/
|
||||
protected void updatePathLabel() {
|
||||
//System.out.println("Update path label: " + currentClassifierModel.checkModelOK());
|
||||
protected void updatePathLabel(DLStatus status) {
|
||||
|
||||
/**
|
||||
* This a bit complicated. We want the label to show errors if they have occured and warning to prompt the
|
||||
* user to do things. The sequence of this is quite important to get right.
|
||||
*/
|
||||
|
||||
pathLabel.setGraphic(null);
|
||||
|
||||
if (currentClassifierModel == null) {
|
||||
//no frameowrk could be selected for the model.
|
||||
pathLabel.setGraphic(createErrorIcon(DLStatus.NO_MODEL_LOADED));
|
||||
pathLabel.setText("No classifier model loaded: Select model");
|
||||
pathLabel.setTooltip(new Tooltip("Use the browse button/ URI botton to select a model or select a default model"));
|
||||
}
|
||||
|
||||
else if (!currentClassifierModel.checkModelOK()) {
|
||||
pathLabel.setText("The model could not be loaded?");
|
||||
pathLabel.setTooltip(new Tooltip("Use the browse button/ URI botton to select a model or select a default model"));
|
||||
|
||||
if (currentClassifierModel.getModelStatus().isError()) {
|
||||
pathLabel.setGraphic(createErrorIcon(currentClassifierModel.getModelStatus()));
|
||||
pathLabel.setText(currentClassifierModel.getModelStatus().getName());
|
||||
pathLabel.setTooltip(new Tooltip(currentClassifierModel.getModelStatus().getDescription()));
|
||||
}
|
||||
else if (status.isError()) {
|
||||
pathLabel.setGraphic(createErrorIcon(status));
|
||||
pathLabel.setText(status.getName());
|
||||
pathLabel.setTooltip(new Tooltip(status.getDescription()));
|
||||
}
|
||||
else {
|
||||
pathLabel .setText(new File(this.currentSelectedFile).getName());
|
||||
//show a warning icon if needed.
|
||||
String tooltip = "";
|
||||
try {
|
||||
pathLabel.setTooltip(new Tooltip(this.currentSelectedFile.getPath()
|
||||
+ "\n" +" Processor CPU " + Device.cpu() + " " + Device.gpu()));
|
||||
tooltip += (this.currentSelectedFile.getPath()
|
||||
+ "\n" +" Processor CPU " + Device.cpu() + " " + Device.gpu());
|
||||
tooltip+="\n";
|
||||
}
|
||||
catch (Exception e) {
|
||||
//sometimes get an error here for some reason
|
||||
//does not make a difference other than tooltip.
|
||||
System.err.println("StandardModelPane: Error getting the default device!");
|
||||
}
|
||||
if (status.isWarning()) {
|
||||
tooltip+="Warning: " + status.getDescription();
|
||||
}
|
||||
pathLabel.setTooltip(new Tooltip(tooltip));
|
||||
}
|
||||
|
||||
}
|
||||
@ -418,16 +504,39 @@ public class DLModelSelectPane extends PamBorderPane {
|
||||
|
||||
public LoadTask(URI uri) {
|
||||
this.uri=uri;
|
||||
|
||||
|
||||
//TODO - not the best as some other part of the program could be using download listeners...
|
||||
dlControl.getDownloadManager().clearDownloadListeners();
|
||||
|
||||
dlControl.getDownloadManager().addDownloadListener((status, bytesDownLoaded)->{
|
||||
|
||||
this.updateProgress(-1, 1); //set to intermedaite
|
||||
this.updateMessage(String.format("Download %.2f MB", ((double) bytesDownLoaded)/1024./1024.));
|
||||
|
||||
|
||||
updateMessage( status, bytesDownLoaded);
|
||||
});
|
||||
|
||||
}
|
||||
|
||||
private void updateMessage(DLStatus status, long bytesDownLoaded) {
|
||||
//the updates have their own messages but let's take some more control here.
|
||||
this.updateProgress(-1, 1); //set to intermediate
|
||||
System.out.println("Status: " + status);
|
||||
switch (status) {
|
||||
case CONNECTION_TO_URL:
|
||||
this.updateMessage("Checking URL");
|
||||
break;
|
||||
case DOWNLOADING:
|
||||
this.updateMessage(String.format("Download %.2f MB", ((double) bytesDownLoaded)/1024./1024.));
|
||||
break;
|
||||
case DOWNLOAD_FINISHED:
|
||||
this.updateMessage("Download complete");
|
||||
break;
|
||||
case DOWNLOAD_STARTING:
|
||||
this.updateMessage("Download starting");
|
||||
break;
|
||||
default:
|
||||
this.updateMessage(status.getDescription());
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
@ -474,7 +583,7 @@ public class DLModelSelectPane extends PamBorderPane {
|
||||
pathLabel.textProperty().unbind();
|
||||
modelLoadIndicator.progressProperty().unbind();
|
||||
|
||||
updatePathLabel();
|
||||
updatePathLabel(this.getValue());
|
||||
}
|
||||
|
||||
@Override protected void succeeded() {
|
||||
|
@ -1,11 +1,10 @@
|
||||
package rawDeepLearningClassifier.layoutFX;
|
||||
|
||||
import java.net.URI;
|
||||
import java.util.ArrayList;
|
||||
|
||||
import org.controlsfx.control.PopOver;
|
||||
|
||||
import PamController.FlipSettingsPane;
|
||||
import PamController.PamGUIManager;
|
||||
import PamController.SettingsPane;
|
||||
import PamDetection.RawDataUnit;
|
||||
import PamView.dialog.warn.WarnOnce;
|
||||
@ -17,16 +16,12 @@ import javafx.application.Platform;
|
||||
import javafx.geometry.Insets;
|
||||
import javafx.geometry.Pos;
|
||||
import javafx.scene.control.Button;
|
||||
import javafx.scene.control.ComboBox;
|
||||
import javafx.scene.control.Label;
|
||||
import javafx.scene.control.PopupControl;
|
||||
import javafx.scene.control.Spinner;
|
||||
import javafx.scene.control.Tooltip;
|
||||
import javafx.scene.control.Alert.AlertType;
|
||||
import javafx.scene.layout.HBox;
|
||||
import javafx.scene.layout.Pane;
|
||||
import javafx.stage.Stage;
|
||||
import pamViewFX.PAMGuiFXSettings;
|
||||
import pamViewFX.PamGuiManagerFX;
|
||||
import pamViewFX.fxGlyphs.PamGlyphDude;
|
||||
import pamViewFX.fxNodes.PamBorderPane;
|
||||
@ -39,8 +34,8 @@ import pamViewFX.fxNodes.pamDialogFX.PamDialogFX;
|
||||
import pamViewFX.fxNodes.utilityPanes.GroupedSourcePaneFX;
|
||||
import pamViewFX.fxNodes.utilityPanes.PamToggleSwitch;
|
||||
import rawDeepLearningClassifier.DLControl;
|
||||
import rawDeepLearningClassifier.DLStatus;
|
||||
import rawDeepLearningClassifier.RawDLParams;
|
||||
import rawDeepLearningClassifier.dlClassification.DLClassiferModel;
|
||||
import warnings.PamWarning;
|
||||
|
||||
/**
|
||||
@ -49,7 +44,7 @@ import warnings.PamWarning;
|
||||
* @author Jamie Macaulay
|
||||
*
|
||||
*/
|
||||
public class RawDLSettingsPane extends SettingsPane<RawDLParams>{
|
||||
public class DLSettingsPane extends SettingsPane<RawDLParams>{
|
||||
|
||||
|
||||
public static double MAX_WIDTH = 270;
|
||||
@ -116,15 +111,11 @@ public class RawDLSettingsPane extends SettingsPane<RawDLParams>{
|
||||
|
||||
private Label infoLabel;
|
||||
|
||||
private Object flipPane;
|
||||
|
||||
private PopupControl advLabel;
|
||||
|
||||
private DLModelSelectPane modelSelectPane;
|
||||
|
||||
|
||||
|
||||
public RawDLSettingsPane(DLControl dlControl){
|
||||
public DLSettingsPane(DLControl dlControl){
|
||||
super(null);
|
||||
this.dlControl=dlControl;
|
||||
// Button newButton=new Button("Test");
|
||||
@ -140,9 +131,12 @@ public class RawDLSettingsPane extends SettingsPane<RawDLParams>{
|
||||
mainPane=new PamBorderPane();
|
||||
mainPane.setCenter(createDLPane());
|
||||
mainPane.setPadding(new Insets(5,5,5,5));
|
||||
mainPane.setMinHeight(430);
|
||||
mainPane.setMaxWidth(MAX_WIDTH);
|
||||
mainPane.setPrefWidth(MAX_WIDTH);
|
||||
|
||||
if (!PamGUIManager.isFX()){
|
||||
mainPane.setMinHeight(430);
|
||||
mainPane.setMaxWidth(MAX_WIDTH);
|
||||
mainPane.setPrefWidth(MAX_WIDTH);
|
||||
}
|
||||
//this.getAdvPane().setMaxWidth(MAX_WIDTH);
|
||||
|
||||
|
||||
@ -377,8 +371,16 @@ public class RawDLSettingsPane extends SettingsPane<RawDLParams>{
|
||||
System.out.println("Set CLASSIFIER PANE: " + modelSelectPane.currentClassifierModel);
|
||||
|
||||
if (modelSelectPane.currentClassifierModel!=null && modelSelectPane.currentClassifierModel.getModelUI()!=null) {
|
||||
|
||||
classifierPane.setCenter(modelSelectPane.currentClassifierModel.getModelUI().getSettingsPane().getContentNode());
|
||||
modelSelectPane.currentClassifierModel.getModelUI().setParams();
|
||||
|
||||
if (modelSelectPane.currentClassifierModel!=null) {
|
||||
modelSelectPane.currentClassifierModel.getModelUI().setParams();
|
||||
}
|
||||
else {
|
||||
classifierPane.setCenter(null);
|
||||
}
|
||||
|
||||
}
|
||||
else {
|
||||
classifierPane.setCenter(null);
|
||||
@ -391,6 +393,7 @@ public class RawDLSettingsPane extends SettingsPane<RawDLParams>{
|
||||
|
||||
if (currParams==null ) currParams = new RawDLParams();
|
||||
|
||||
@SuppressWarnings("rawtypes")
|
||||
PamDataBlock rawDataBlock = sourcePane.getSource();
|
||||
if (rawDataBlock == null){
|
||||
Platform.runLater(()->{
|
||||
@ -451,17 +454,44 @@ public class RawDLSettingsPane extends SettingsPane<RawDLParams>{
|
||||
this.modelSelectPane.currentClassifierModel.getModelUI().getParams();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
currParams.modelURI = this.modelSelectPane.currentSelectedFile;
|
||||
|
||||
return currParams;
|
||||
}
|
||||
|
||||
|
||||
public static PamWarning statusToWarnings(DLStatus dlStatus) {
|
||||
PamWarning pamWarning = new PamWarning(dlStatus.getName(), dlStatus.getDescription(), dlStatus.isError() ? 2 : 1);
|
||||
return pamWarning;
|
||||
}
|
||||
|
||||
/**
|
||||
* Show a warning dialog for the status
|
||||
* @param the status to show
|
||||
*/
|
||||
public void showWarning(DLStatus dlWarning) {
|
||||
ArrayList<PamWarning> dlWarnings = new ArrayList<PamWarning>();
|
||||
dlWarnings.add(statusToWarnings(dlWarning));
|
||||
showWarning(dlWarnings);
|
||||
}
|
||||
|
||||
/**
|
||||
* Show a warning dialog.
|
||||
* @param the warning to show.
|
||||
*/
|
||||
public void showWarning(PamWarning dlWarning) {
|
||||
ArrayList<PamWarning> dlWarnings = new ArrayList<PamWarning>();
|
||||
dlWarnings.add(dlWarning);
|
||||
showWarning(dlWarnings);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Show a warning dialog.
|
||||
* @param dlWarnings - list of warnings - the most important will be shown.
|
||||
*/
|
||||
public void showWarnings(ArrayList<PamWarning> dlWarnings) {
|
||||
public void showWarning(ArrayList<PamWarning> dlWarnings) {
|
||||
|
||||
if (dlWarnings==null || dlWarnings.size()<1) return;
|
||||
|
||||
@ -480,6 +510,7 @@ public class RawDLSettingsPane extends SettingsPane<RawDLParams>{
|
||||
final boolean errorF = error;
|
||||
Platform.runLater(()->{
|
||||
WarnOnce.showWarningFX(null, "Deep Learning Settings Warning", warningsF , errorF ? AlertType.ERROR : AlertType.WARNING);
|
||||
// WarnOnce.showWarning( "Deep Learning Settings Warning", warningsF , WarnOnce.WARNING_MESSAGE);
|
||||
});
|
||||
|
||||
//user presses OK - these warnings are just a message - they do not prevent running the module.
|
||||
@ -500,7 +531,6 @@ public class RawDLSettingsPane extends SettingsPane<RawDLParams>{
|
||||
}
|
||||
|
||||
// dlModelBox.getSelectionModel().select(currParams.modelSelection);
|
||||
|
||||
windowLength.getValueFactory().setValue(currParams.rawSampleSize);
|
||||
|
||||
hopLength.getValueFactory().setValue(currParams.sampleHop);
|
||||
@ -514,17 +544,16 @@ public class RawDLSettingsPane extends SettingsPane<RawDLParams>{
|
||||
enableControls();
|
||||
|
||||
setSegInfoLabel();
|
||||
|
||||
|
||||
// //set up the model and the custom pane if necessary.
|
||||
//
|
||||
|
||||
// //set up the model and the custom pane if necessary.
|
||||
this.modelSelectPane.loadNewModel(currParams.modelURI);
|
||||
//this.modelSelectPane.updatePathLabel();
|
||||
this.setClassifierPane();
|
||||
|
||||
//For some reason, in the FX GUI, this causes a root used in multiple scenes exceptions...not sure why.
|
||||
//sourcePane.getChannelValidator().validate();
|
||||
Platform.runLater(()->{
|
||||
sourcePane.getChannelValidator().validate();
|
||||
});
|
||||
|
||||
}
|
||||
|
||||
@ -553,6 +582,7 @@ public class RawDLSettingsPane extends SettingsPane<RawDLParams>{
|
||||
* Get the data block currently selected in the pane.
|
||||
* @return the data block currently selected in the pane.
|
||||
*/
|
||||
@SuppressWarnings("rawtypes")
|
||||
public PamDataBlock getSelectedParentDataBlock() {
|
||||
return sourcePane.getSource();
|
||||
}
|
||||
@ -565,6 +595,34 @@ public class RawDLSettingsPane extends SettingsPane<RawDLParams>{
|
||||
return dlControl;
|
||||
}
|
||||
|
||||
/**
|
||||
* Convenience class to set the segment length in samples from milliseconds
|
||||
* @param defaultSegmentLen - the segment length in milliseconds.
|
||||
*/
|
||||
public void setSegmentLength(Double defaultSegmentLen) {
|
||||
if (defaultSegmentLen==null) return;
|
||||
|
||||
|
||||
double sR = getDLControl().getSettingsPane().getSelectedParentDataBlock().getSampleRate();
|
||||
|
||||
System.out.println("Set the segment length: " + defaultSegmentLen + " sR " + sR);
|
||||
|
||||
//automatically set the default segment length.
|
||||
getDLControl().getSettingsPane().getSegmentLenSpinner().getValueFactory().setValue((int) (sR*defaultSegmentLen/1000.));
|
||||
}
|
||||
|
||||
/**
|
||||
* Convenience class to set the hop length in samples from milliseconds
|
||||
* @param defaultSegmentLen - the segment length in milliseconds.
|
||||
*/
|
||||
public void setHopLength(Double hopLength) {
|
||||
if (hopLength==null) return;
|
||||
|
||||
double sR = getDLControl().getSettingsPane().getSelectedParentDataBlock().getSampleRate();
|
||||
//automatically set the default segment length.
|
||||
getDLControl().getSettingsPane().getHopLenSpinner().getValueFactory().setValue((int) (sR*hopLength/1000.));
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
@ -0,0 +1,170 @@
|
||||
package rawDeepLearningClassifier.layoutFX.defaultModels;
|
||||
|
||||
import java.awt.Desktop;
|
||||
import java.io.IOException;
|
||||
import java.net.URI;
|
||||
import java.net.URISyntaxException;
|
||||
|
||||
import javafx.application.HostServices;
|
||||
import javafx.beans.property.ObjectProperty;
|
||||
import javafx.beans.property.SimpleObjectProperty;
|
||||
import javafx.geometry.Insets;
|
||||
import javafx.geometry.Pos;
|
||||
import javafx.geometry.Side;
|
||||
import javafx.scene.Node;
|
||||
import javafx.scene.control.Hyperlink;
|
||||
import javafx.scene.control.Label;
|
||||
import javafx.scene.layout.BorderPane;
|
||||
import javafx.scene.layout.Pane;
|
||||
import javafx.scene.layout.Priority;
|
||||
import javafx.scene.layout.Region;
|
||||
import javafx.scene.layout.StackPane;
|
||||
import javafx.scene.layout.VBox;
|
||||
import pamViewFX.PamGuiManagerFX;
|
||||
import pamViewFX.fxGlyphs.PamGlyphDude;
|
||||
import pamViewFX.fxNodes.PamBorderPane;
|
||||
import pamViewFX.fxNodes.PamButton;
|
||||
import pamViewFX.fxNodes.PamStackPane;
|
||||
import pamViewFX.fxNodes.PamVBox;
|
||||
import pamViewFX.fxNodes.hidingPane.HidingPane;
|
||||
import rawDeepLearningClassifier.defaultModels.DLDefaultModelManager;
|
||||
import rawDeepLearningClassifier.defaultModels.DLModel;
|
||||
|
||||
/**
|
||||
* Pane which allows users to view and select default models.
|
||||
*/
|
||||
public class DefaultModelPane extends PamBorderPane{
|
||||
|
||||
/**
|
||||
* Reference to the deafult model manager that contains the default models.
|
||||
*/
|
||||
private DLDefaultModelManager defaultModelManager;
|
||||
|
||||
|
||||
private PamBorderPane hidingPaneContent;
|
||||
|
||||
|
||||
private HidingPane hidingPane;
|
||||
|
||||
ObjectProperty<DLModel> defaultModel = new SimpleObjectProperty();
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Constructor for the DefaultModelPane
|
||||
* @param defaultModelManager - the default model manager to use.
|
||||
*/
|
||||
public DefaultModelPane(DLDefaultModelManager defaultModelManager) {
|
||||
this.defaultModelManager=defaultModelManager;
|
||||
this.setCenter(createDefaultModelPane() );
|
||||
}
|
||||
|
||||
|
||||
|
||||
private Pane createDefaultModelPane() {
|
||||
|
||||
PamVBox vBox = new PamVBox();
|
||||
|
||||
// vBox.setSpacing(5);
|
||||
|
||||
Label label = new Label("Default Models");
|
||||
PamGuiManagerFX.titleFont2style(label);
|
||||
|
||||
vBox.getChildren().add(label);
|
||||
// vBox.setPrefWidth(120);
|
||||
|
||||
hidingPaneContent= new PamBorderPane();
|
||||
hidingPaneContent.setPrefWidth(150);
|
||||
hidingPane = new HidingPane(Side.RIGHT, hidingPaneContent, vBox, true, 0);
|
||||
|
||||
PamButton button;
|
||||
for (int i=0; i<defaultModelManager.getNumDefaultModels(); i++) {
|
||||
final int ii = i;
|
||||
button= new PamButton(defaultModelManager.getDefaultModel(ii).getName());
|
||||
button.prefWidthProperty().bind(vBox.widthProperty());
|
||||
button.setOnAction((action)->{
|
||||
hidingPaneContent.setCenter(createModelPane(defaultModelManager.getDefaultModel(ii)));
|
||||
hidingPane.showHidePane(true);
|
||||
});
|
||||
|
||||
if (i>0 && i<defaultModelManager.getNumDefaultModels()-1) {
|
||||
button.setStyle("-fx-border-radius: 0 0 0 0; -fx-background-radius: 0 0 0 0");
|
||||
}
|
||||
else if (i==0) {
|
||||
button.setStyle("-fx-border-radius: 5 5 0 0; -fx-background-radius: 5 5 0 0");
|
||||
}
|
||||
else {
|
||||
button.setStyle("-fx-border-radius: 0 0 5 5 ; -fx-background-radius: 0 0 5 5");
|
||||
}
|
||||
|
||||
vBox.getChildren().add(button);
|
||||
}
|
||||
|
||||
hidingPane.setStyle("-fx-background-color: -fx-base");
|
||||
// this.setStyle("-fx-background-color: -fx-base");
|
||||
|
||||
PamStackPane mainHolder = new PamStackPane();
|
||||
mainHolder.getChildren().addAll(vBox, hidingPane);
|
||||
StackPane.setAlignment(hidingPane, Pos.TOP_RIGHT);
|
||||
|
||||
return mainHolder;
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
private Node createModelPane(DLModel dlModel) {
|
||||
|
||||
Label titleLabel = new Label(dlModel.getName());
|
||||
titleLabel.setWrapText(true);
|
||||
PamGuiManagerFX.titleFont2style(titleLabel);
|
||||
titleLabel.setPadding(new Insets(25,0,0,0));
|
||||
|
||||
hidingPane.getChildren().add(titleLabel);
|
||||
|
||||
PamVBox vBox = new PamVBox();
|
||||
vBox.setSpacing(5);;
|
||||
|
||||
Label descriptionLabel = new Label(dlModel.getDescription());
|
||||
descriptionLabel.setWrapText(true);
|
||||
|
||||
Hyperlink link = new Hyperlink(dlModel.getCitation());
|
||||
link.setWrapText(true);
|
||||
link.setOnAction((action)->{
|
||||
try {
|
||||
Desktop.getDesktop().browse(dlModel.getCitationLink());
|
||||
} catch (IOException e) {
|
||||
// TODO Auto-generated catch block
|
||||
e.printStackTrace();
|
||||
}
|
||||
// HostServices.getInstance(this).getHostServices().showDocument(yahooURL)
|
||||
});
|
||||
|
||||
|
||||
PamButton importButton = new PamButton("Import");
|
||||
importButton.setGraphic(PamGlyphDude.createPamIcon("mdi2d-download", PamGuiManagerFX.iconSize));
|
||||
importButton.setOnAction((action)->{
|
||||
defaultModel.set(dlModel);
|
||||
});
|
||||
|
||||
PamBorderPane buttonHolder = new PamBorderPane();
|
||||
buttonHolder.setRight(importButton);
|
||||
BorderPane.setAlignment(importButton, Pos.BOTTOM_RIGHT);
|
||||
VBox.setVgrow(buttonHolder, Priority.ALWAYS);
|
||||
|
||||
|
||||
vBox.getChildren().addAll(titleLabel, descriptionLabel, link, buttonHolder);
|
||||
vBox.setPrefHeight(200);
|
||||
|
||||
return vBox;
|
||||
}
|
||||
|
||||
|
||||
public ObjectProperty<DLModel> defaultModelProperty() {
|
||||
return defaultModel;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
}
|
@ -150,10 +150,10 @@ public class DLTransformsPane extends PamBorderPane {
|
||||
ArrayList<DLTransformPane> dlTransformPanes = new ArrayList<DLTransformPane>();
|
||||
|
||||
sampleRate=-1;
|
||||
|
||||
// for (int i=0; i<dlTransforms.size() ; i++) {
|
||||
// System.out.println("Set DL transfroms: " + dlTransforms.get(i).getDLTransformType() + " " + ((SimpleTransform) dlTransforms.get(i)).getParams());
|
||||
// }
|
||||
//
|
||||
// for (int i=0; i<dlTransforms.size() ; i++) {
|
||||
// System.out.println("Set DL transfroms: " + dlTransforms.get(i).getDLTransformType() + " " + ((SimpleTransform) dlTransforms.get(i)).getParams());
|
||||
// }
|
||||
|
||||
DLTransformPane transformPane;
|
||||
//create a pane for each transform
|
||||
@ -164,6 +164,10 @@ public class DLTransformsPane extends PamBorderPane {
|
||||
}
|
||||
|
||||
transformPane = DataTransformPaneFactory.getSettingsPane(dlTransforms.get(i));
|
||||
|
||||
|
||||
System.out.println("Set DL transfroms: " + dlTransforms.get(i).getDLTransformType() + " " + ((SimpleTransform) dlTransforms.get(i)).getParams());
|
||||
|
||||
|
||||
//there must be a transform pane or else this will break.
|
||||
dlTransformPanes.add(transformPane);
|
||||
|
@ -42,6 +42,7 @@ public class DataTransformPaneFactory {
|
||||
DLTransformPane settingsPane = null;
|
||||
switch (dlTransfrom.getDLTransformType()) {
|
||||
case DECIMATE:
|
||||
case DECIMATE_SCIPY:
|
||||
double sR;
|
||||
if (((SimpleTransform) dlTransfrom).getParams()!=null){
|
||||
sR = ((SimpleTransform) dlTransfrom).getParams()[0].doubleValue();
|
||||
|
@ -1,4 +1,4 @@
|
||||
package test.java.rawDeepLearningClassifier;
|
||||
package test.rawDeepLearningClassifier;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
|
||||
@ -18,11 +18,14 @@ import rawDeepLearningClassifier.dlClassification.genericModel.GenericModelParse
|
||||
class DLJSONParserTest {
|
||||
|
||||
@Test
|
||||
void test() {
|
||||
public void test() {
|
||||
|
||||
|
||||
//load an old file
|
||||
String relJSONpath = "./src/test/resources/rawDeepLearningClassifier/Generic/right_whale/legacy_format/right_whale_DL_settings.pdtf";
|
||||
|
||||
System.out.println("Path: " + relJSONpath);
|
||||
|
||||
Path path = Paths.get(relJSONpath);
|
||||
|
||||
GenericModelParams genericParmas = new GenericModelParams();
|
@ -1,4 +1,4 @@
|
||||
package test.java.rawDeepLearningClassifier;
|
||||
package test.rawDeepLearningClassifier;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
import rawDeepLearningClassifier.DLControl;
|
||||
@ -6,7 +6,6 @@ import rawDeepLearningClassifier.dlClassification.ketos.KetosClassifier;
|
||||
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
|
||||
public class KetosClassifierTest {
|
||||
|
||||
// /**
|
||||
@ -63,6 +62,6 @@ public class KetosClassifierTest {
|
||||
public void ketosProcessTest() {
|
||||
System.out.println("hello unit test complete");
|
||||
|
||||
assertEquals(2, 1+1);
|
||||
assertEquals(2, 2);
|
||||
}
|
||||
}
|
@ -1,4 +1,4 @@
|
||||
package test.java.rawDeepLearningClassifier;
|
||||
package test.rawDeepLearningClassifier;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
|
@ -0,0 +1,50 @@
|
||||
{
|
||||
"framework_info": {"framework": "Bespoke"},
|
||||
"model_info": {
|
||||
"output_shape": [
|
||||
-1,
|
||||
2
|
||||
],
|
||||
"input_shape": [
|
||||
-1,
|
||||
40,
|
||||
40,
|
||||
1
|
||||
]
|
||||
},
|
||||
"class_info": {
|
||||
"name_class": [
|
||||
"Noise",
|
||||
"Right Whale"
|
||||
],
|
||||
"num_class": 2
|
||||
},
|
||||
"transforms": [
|
||||
{
|
||||
"name": "norm_row_sum",
|
||||
"params": {}
|
||||
},
|
||||
{
|
||||
"name": "spectrogram",
|
||||
"params": {
|
||||
"fft": 256,
|
||||
"hop": 100
|
||||
}
|
||||
},
|
||||
{
|
||||
"name": "load_audio",
|
||||
"params": {"sr": 2000}
|
||||
},
|
||||
{
|
||||
"name": "freq_compression",
|
||||
"params": {
|
||||
"bins": 40,
|
||||
"fmin": 47,
|
||||
"fmax": 357
|
||||
}
|
||||
}
|
||||
],
|
||||
"description": "Metadata for acoustic deep learning",
|
||||
"version_info": {"version": 1},
|
||||
"seg_size": {"size_ms": 2000}
|
||||
}
|
@ -1,5 +0,0 @@
|
||||
package test;
|
||||
|
||||
public class DummyPamControllerInterface {
|
||||
|
||||
}
|
@ -1 +0,0 @@
|
||||
{"framework_info":{"framework":"Bespoke"},"model_info":{"output_shape":[-1,2],"input_shape":[-1,40,40,1]},"class_info":{"name_class":["Noise","Right Whale"],"num_class":2},"transforms":[{"name":"norm_row_sum","params":{}},{"name":"spectrogram","params":{"fft":256,"hop":100}},{"name":"load_audio","params":{"sr":2000}},{"name":"freq_compression","params":{"bins":40,"fmin":47,"fmax":357}}],"version_info":{"version":1},"seg_size":{"size_ms":2000}}
|
Loading…
Reference in New Issue
Block a user