commit 29/01/2026

This commit is contained in:
2026-01-29 22:58:20 +07:00
parent b04e168b9a
commit b90982366d
19 changed files with 421 additions and 111 deletions

4
.gitignore vendored
View File

@@ -3,6 +3,7 @@ out/
!**/src/main/**/out/ !**/src/main/**/out/
!**/src/test/**/out/ !**/src/test/**/out/
### Kotlin ### ### Kotlin ###
.kotlin .kotlin
@@ -46,3 +47,6 @@ chimedown.wav
chimeup.wav chimeup.wav
silence1s.wav silence1s.wav
silencehalf.wav silencehalf.wav
bass*.dll
bass*.so
sdx.dll

115
.idea/artifacts/AAS_NewGen_jar.xml generated Normal file
View File

@@ -0,0 +1,115 @@
<component name="ArtifactManager">
<artifact type="jar" name="AAS_NewGen:jar">
<output-path>$PROJECT_DIR$/out/artifacts/AAS_NewGen_jar</output-path>
<root id="archive" name="AAS_NewGen.jar">
<element id="module-output" name="AAS_NewGen" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/jetbrains/kotlinx/kotlinx-coroutines-core/1.9.0/kotlinx-coroutines-core-1.9.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/jetbrains/kotlinx/kotlinx-coroutines-core-jvm/1.9.0/kotlinx-coroutines-core-jvm-1.9.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/jetbrains/annotations/23.0.0/annotations-23.0.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/jetbrains/kotlin/kotlin-stdlib/2.0.0/kotlin-stdlib-2.0.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/fasterxml/jackson/module/jackson-module-kotlin/2.17.2/jackson-module-kotlin-2.17.2.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/fasterxml/jackson/core/jackson-databind/2.17.2/jackson-databind-2.17.2.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/fasterxml/jackson/core/jackson-core/2.17.2/jackson-core-2.17.2.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/fasterxml/jackson/core/jackson-annotations/2.17.2/jackson-annotations-2.17.2.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/jetbrains/kotlin/kotlin-reflect/1.7.22/kotlin-reflect-1.7.22.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/jetbrains/kotlin/kotlin-stdlib/1.7.22/kotlin-stdlib-1.7.22.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/jetbrains/kotlin/kotlin-stdlib-common/1.7.22/kotlin-stdlib-common-1.7.22.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/jetbrains/annotations/13.0/annotations-13.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/net/java/dev/jna/jna/5.18.1/jna-5.18.1.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/cloud/google-cloud-texttospeech/2.81.0/google-cloud-texttospeech-2.81.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/io/grpc/grpc-api/1.76.0/grpc-api-1.76.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/code/findbugs/jsr305/3.0.2/jsr305-3.0.2.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/errorprone/error_prone_annotations/2.42.0/error_prone_annotations-2.42.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/io/grpc/grpc-stub/1.76.0/grpc-stub-1.76.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/codehaus/mojo/animal-sniffer-annotations/1.24/animal-sniffer-annotations-1.24.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/io/grpc/grpc-protobuf/1.76.0/grpc-protobuf-1.76.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/io/grpc/grpc-protobuf-lite/1.76.0/grpc-protobuf-lite-1.76.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/api/api-common/2.55.1/api-common-2.55.1.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/auto/value/auto-value-annotations/1.11.0/auto-value-annotations-1.11.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/javax/annotation/javax.annotation-api/1.3.2/javax.annotation-api-1.3.2.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/j2objc/j2objc-annotations/3.1/j2objc-annotations-3.1.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/protobuf/protobuf-java/3.25.8/protobuf-java-3.25.8.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/api/grpc/proto-google-common-protos/2.63.1/proto-google-common-protos-2.63.1.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/api/grpc/proto-google-cloud-texttospeech-v1/2.81.0/proto-google-cloud-texttospeech-v1-2.81.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/api/grpc/proto-google-cloud-texttospeech-v1beta1/0.170.0/proto-google-cloud-texttospeech-v1beta1-0.170.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/guava/guava/33.5.0-jre/guava-33.5.0-jre.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/guava/failureaccess/1.0.3/failureaccess-1.0.3.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/guava/listenablefuture/9999.0-empty-to-avoid-conflict-with-guava/listenablefuture-9999.0-empty-to-avoid-conflict-with-guava.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/jspecify/jspecify/1.0.0/jspecify-1.0.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/api/gax/2.72.1/gax-2.72.1.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/auth/google-auth-library-credentials/1.40.0/google-auth-library-credentials-1.40.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/protobuf/protobuf-java-util/3.25.8/protobuf-java-util-3.25.8.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/io/opencensus/opencensus-api/0.31.1/opencensus-api-0.31.1.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/io/grpc/grpc-context/1.76.0/grpc-context-1.76.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/auth/google-auth-library-oauth2-http/1.40.0/google-auth-library-oauth2-http-1.40.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/api/gax-grpc/2.72.1/gax-grpc-2.72.1.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/io/grpc/grpc-inprocess/1.76.0/grpc-inprocess-1.76.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/io/grpc/grpc-core/1.76.0/grpc-core-1.76.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/android/annotations/4.1.1.4/annotations-4.1.1.4.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/io/grpc/grpc-alts/1.76.0/grpc-alts-1.76.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/io/grpc/grpc-grpclb/1.76.0/grpc-grpclb-1.76.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/conscrypt/conscrypt-openjdk-uber/2.5.2/conscrypt-openjdk-uber-2.5.2.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/io/grpc/grpc-auth/1.76.0/grpc-auth-1.76.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/io/grpc/grpc-netty-shaded/1.76.0/grpc-netty-shaded-1.76.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/io/grpc/grpc-util/1.76.0/grpc-util-1.76.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/io/perfmark/perfmark-api/0.27.0/perfmark-api-0.27.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/io/grpc/grpc-googleapis/1.76.0/grpc-googleapis-1.76.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/io/grpc/grpc-xds/1.76.0/grpc-xds-1.76.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/io/grpc/grpc-services/1.76.0/grpc-services-1.76.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/re2j/re2j/1.8/re2j-1.8.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/api/gax-httpjson/2.72.1/gax-httpjson-2.72.1.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/code/gson/gson/2.12.1/gson-2.12.1.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/http-client/google-http-client/2.0.2/google-http-client-2.0.2.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/apache/httpcomponents/httpclient/4.5.14/httpclient-4.5.14.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/commons-codec/commons-codec/1.18.0/commons-codec-1.18.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/apache/httpcomponents/httpcore/4.4.16/httpcore-4.4.16.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/io/opencensus/opencensus-contrib-http-util/0.31.1/opencensus-contrib-http-util-0.31.1.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/http-client/google-http-client-gson/2.0.2/google-http-client-gson-2.0.2.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/threeten/threetenbp/1.7.0/threetenbp-1.7.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/github/oshi/oshi-core/6.9.0/oshi-core-6.9.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/net/java/dev/jna/jna/5.17.0/jna-5.17.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/net/java/dev/jna/jna-platform/5.17.0/jna-platform-5.17.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/slf4j/slf4j-api/2.0.17/slf4j-api-2.0.17.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/slf4j/slf4j-simple/2.0.17/slf4j-simple-2.0.17.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/io/javalin/javalin/6.7.0/javalin-6.7.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/eclipse/jetty/jetty-server/11.0.25/jetty-server-11.0.25.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/eclipse/jetty/jetty-http/11.0.25/jetty-http-11.0.25.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/eclipse/jetty/jetty-util/11.0.25/jetty-util-11.0.25.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/eclipse/jetty/jetty-io/11.0.25/jetty-io-11.0.25.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/eclipse/jetty/toolchain/jetty-jakarta-servlet-api/5.0.2/jetty-jakarta-servlet-api-5.0.2.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/eclipse/jetty/websocket/websocket-jetty-server/11.0.25/websocket-jetty-server-11.0.25.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/eclipse/jetty/jetty-servlet/11.0.25/jetty-servlet-11.0.25.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/eclipse/jetty/jetty-security/11.0.25/jetty-security-11.0.25.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/eclipse/jetty/jetty-webapp/11.0.25/jetty-webapp-11.0.25.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/eclipse/jetty/jetty-xml/11.0.25/jetty-xml-11.0.25.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/eclipse/jetty/websocket/websocket-jetty-api/11.0.25/websocket-jetty-api-11.0.25.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/eclipse/jetty/websocket/websocket-jetty-common/11.0.25/websocket-jetty-common-11.0.25.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/eclipse/jetty/websocket/websocket-core-common/11.0.25/websocket-core-common-11.0.25.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/eclipse/jetty/websocket/websocket-servlet/11.0.25/websocket-servlet-11.0.25.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/eclipse/jetty/websocket/websocket-core-server/11.0.25/websocket-core-server-11.0.25.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/jetbrains/kotlin/kotlin-stdlib-jdk8/1.9.25/kotlin-stdlib-jdk8-1.9.25.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/jetbrains/kotlin/kotlin-stdlib/1.9.25/kotlin-stdlib-1.9.25.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/jetbrains/kotlin/kotlin-stdlib-jdk7/1.9.25/kotlin-stdlib-jdk7-1.9.25.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/../../../../../../SLC/Apache POI/poi-5.3.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/../../../../../../SLC/Apache POI/xmlbeans-5.2.1.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/../../../../../../SLC/Apache POI/poi-ooxml-5.3.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/../../../../../../SLC/Apache POI/log4j-api-2.23.1.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/../../../../../../SLC/Apache POI/SparseBitSet-1.3.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/../../../../../../SLC/Apache POI/commons-io-2.16.1.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/../../../../../../SLC/Apache POI/poi-5.3.0-sources.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/../../../../../../SLC/Apache POI/commons-math3-3.6.1.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/../../../../../../SLC/Apache POI/commons-codec-1.17.1.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/../../../../../../SLC/Apache POI/poi-ooxml-full-5.3.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/../../../../../../SLC/Apache POI/commons-compress-1.26.2.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/../../../../../../SLC/Apache POI/poi-ooxml-5.3.0-sources.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/../../../../../../SLC/Apache POI/poi-ooxml-schemas-4.1.2.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/../../../../../../SLC/Apache POI/commons-collections4-4.4.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/../../../../../../SLC/Apache POI/poi-ooxml-full-5.3.0-sources.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/jetbrains/kotlin/kotlin-stdlib/2.1.21/kotlin-stdlib-2.1.21.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/tinylog/tinylog-impl/2.7.0/tinylog-impl-2.7.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/org/tinylog/tinylog-api/2.7.0/tinylog-api-2.7.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/mysql/mysql-connector-j/8.4.0/mysql-connector-j-8.4.0.jar" path-in-jar="/" />
<element id="extracted-dir" path="$MAVEN_REPOSITORY$/com/google/protobuf/protobuf-java/3.25.1/protobuf-java-3.25.1.jar" path-in-jar="/" />
</root>
</artifact>
</component>

View File

@@ -50,6 +50,10 @@
margin-top: 1rem!important; margin-top: 1rem!important;
} }
.me-1 {
margin-right: .25rem!important;
}
.me-2 { .me-2 {
margin-right: .5rem!important; margin-right: .5rem!important;
} }
@@ -78,6 +82,10 @@
margin-bottom: auto!important; margin-bottom: auto!important;
} }
.ms-1 {
margin-left: .25rem!important;
}
@media (min-width:768px) { @media (min-width:768px) {
.me-md-auto { .me-md-auto {
margin-right: auto!important; margin-right: auto!important;

View File

@@ -54,6 +54,8 @@ function reloadLogs(APIURL = "Log/", date, filter) {
}); });
} }
$(document).ready(function () { $(document).ready(function () {
console.log("log.js ready"); console.log("log.js ready");
let selectedlogdate = ""; let selectedlogdate = "";
@@ -100,4 +102,6 @@ $(document).ready(function () {
$('#btnExport').off('click').on('click', function () { $('#btnExport').off('click').on('click', function () {
DoExport(APIURL, "log.xlsx", { date: selectedlogdate, filter: logfilter }); DoExport(APIURL, "log.xlsx", { date: selectedlogdate, filter: logfilter });
}); });
}); });

View File

@@ -304,6 +304,14 @@ function LiveAudioCommand(command, bz, cbOK = null, cbFail = null) {
window.streamws = null; window.streamws = null;
window.mediasource = null; window.mediasource = null;
/**
* handler for ws_connected, ws_disconnected, ws_message events
*/
ws_connected_handler;
ws_disconnected_handler;
ws_message_handler;
$(document).ready(function () { $(document).ready(function () {
@@ -426,50 +434,64 @@ $(document).ready(function () {
runIntervalJob(); runIntervalJob();
window.addEventListener('ws_connected', () => { if (!ws_connected_handler) {
console.log("overview.js ws_connected event triggered"); ws_connected_handler = function () {
runIntervalJob(); console.log("overview.js ws_connected event triggered");
}); runIntervalJob();
};
}
window.addEventListener('ws_disconnected', () => { if (!ws_disconnected_handler) {
console.log("overview.js ws_disconnected event triggered"); ws_disconnected_handler = function () {
if (intervaljob1) clearInterval(intervaljob1); console.log("overview.js ws_disconnected event triggered");
if (intervaljob2) clearInterval(intervaljob2); if (intervaljob1) clearInterval(intervaljob1);
intervaljob1 = null; if (intervaljob2) clearInterval(intervaljob2);
intervaljob2 = null; intervaljob1 = null;
}); intervaljob2 = null;
window.addEventListener('ws_message', (event) => { };
let rep = event.detail; }
let cmd = rep.reply;
let data = rep.data; if (!ws_message_handler) {
if (cmd && cmd.length > 0) { ws_message_handler = function (event) {
switch (cmd) { let rep = event.detail;
case "getPagingQueue": let cmd = rep.reply;
let pq = JSON.parse(data); let data = rep.data;
window.PagingQueue = []; if (cmd && cmd.length > 0) {
if (Array.isArray(pq) && pq.length > 0) { switch (cmd) {
window.PagingQueue.push(...pq); case "getPagingQueue":
} let pq = JSON.parse(data);
fill_pagingqueuetablebody(window.PagingQueue); window.PagingQueue = [];
break; if (Array.isArray(pq) && pq.length > 0) {
case "getAASQueue": window.PagingQueue.push(...pq);
let aq = JSON.parse(data); }
window.QueueTable = []; fill_pagingqueuetablebody(window.PagingQueue);
if (Array.isArray(aq) && aq.length > 0) { break;
window.QueueTable.push(...aq); case "getAASQueue":
} let aq = JSON.parse(data);
fill_automaticqueuetablebody(window.QueueTable); window.QueueTable = [];
break; if (Array.isArray(aq) && aq.length > 0) {
case "getStreamerOutputs": window.QueueTable.push(...aq);
/** }
* @type {StreamerOutputData[]} fill_automaticqueuetablebody(window.QueueTable);
*/ break;
let so = JSON.parse(data); case "getStreamerOutputs":
UpdateStreamerCard(so); /**
break; * @type {StreamerOutputData[]}
*/
let so = JSON.parse(data);
UpdateStreamerCard(so);
break;
}
} }
} };
}); }
window.removeEventListener('ws_connected', ws_connected_handler);
window.removeEventListener('ws_disconnected', ws_disconnected_handler);
window.removeEventListener('ws_message', ws_message_handler);
window.addEventListener('ws_connected', ws_connected_handler);
window.addEventListener('ws_disconnected', ws_disconnected_handler);
window.addEventListener('ws_message', ws_message_handler);
$(window).on('beforeunload', function () { $(window).on('beforeunload', function () {
console.log("overview.js beforeunload event triggered"); console.log("overview.js beforeunload event triggered");

View File

@@ -217,6 +217,14 @@ $(document).ready(function () {
</div>`; </div>`;
$('#citylist').append(row); $('#citylist').append(row);
}); });
$('#city_selectall').off('click').on('click', function () {
// select all checkboxes
$('#citylist input[type=checkbox]').prop('checked', true);
});
$('#city_clearall').off('click').on('click', function () {
// deselect all checkboxes
$('#citylist input[type=checkbox]').prop('checked', false);
});
} }
function fill_airlinelist() { function fill_airlinelist() {
@@ -231,6 +239,14 @@ $(document).ready(function () {
</div>`; </div>`;
$('#airlinelist').append(row); $('#airlinelist').append(row);
}); });
$('#airline_selectall').off('click').on('click', function () {
// select all checkboxes
$('#airlinelist input[type=checkbox]').prop('checked', true);
});
$('#airline_clearall').off('click').on('click', function () {
// deselect all checkboxes
$('#airlinelist input[type=checkbox]').prop('checked', false);
});
} }
// broadcast zone selection modal elements // broadcast zone selection modal elements
@@ -246,6 +262,14 @@ $(document).ready(function () {
</div>`; </div>`;
$('#broadcastzonelist').append(row); $('#broadcastzonelist').append(row);
}); });
$('#bzone_selectall').off('click').on('click', function () {
// select all checkboxes
$('#broadcastzonelist input[type=checkbox]').prop('checked', true);
});
$('#bzone_clearall').off('click').on('click', function () {
// deselect all checkboxes
$('#broadcastzonelist input[type=checkbox]').prop('checked', false);
});
} }
@@ -263,6 +287,14 @@ $(document).ready(function () {
</div>`; </div>`;
$('#messagebanklist').append(row); $('#messagebanklist').append(row);
}); });
$('#mbank_selectall').off('click').on('click', function () {
// select all checkboxes
$('#messagebanklist input[type=checkbox]').prop('checked', true);
});
$('#mbank_clearall').off('click').on('click', function () {
// deselect all checkboxes
$('#messagebanklist input[type=checkbox]').prop('checked', false);
});
} }

View File

@@ -153,18 +153,38 @@
<div class="modal-body bg-modal-body"> <div class="modal-body bg-modal-body">
<div class="accordion" role="tablist" id="accordion-1"> <div class="accordion" role="tablist" id="accordion-1">
<div class="accordion-item pad-accordion"> <div class="accordion-item pad-accordion">
<h2 class="accordion-header" role="tab"><button class="accordion-button bg-heading1" type="button" data-bs-toggle="collapse" data-bs-target="#accordion-1 .item-1" aria-expanded="true" aria-controls="accordion-1 .item-1">Airline</button></h2> <h2 class="accordion-header" role="tab"><button class="accordion-button collapsed bg-heading1" type="button" data-bs-toggle="collapse" data-bs-target="#accordion-1 .item-1" aria-expanded="false" aria-controls="accordion-1 .item-1">Airline</button></h2>
<div class="accordion-collapse collapse show item-1" role="tabpanel" data-bs-parent="#accordion-1"> <div class="accordion-collapse collapse item-1" role="tabpanel" data-bs-parent="#accordion-1">
<div class="accordion-body"> <div class="accordion-body">
<ul id="airlinelist"></ul> <div class="col w-100 h-100">
<div class="row">
<div class="col">
<ul id="airlinelist"></ul>
</div>
</div>
<div class="row">
<div class="col"><button class="btn btn-primary w-100 h-100 ms-1 me-1" id="airline_selectall" type="button">Select All</button></div>
<div class="col"><button class="btn btn-primary w-100 h-100 ms-1 me-1" id="airline_clearall" type="button">Clear All</button></div>
</div>
</div>
</div> </div>
</div> </div>
</div> </div>
<div class="accordion-item pad-accordion"> <div class="accordion-item pad-accordion">
<h2 class="accordion-header" role="tab"><button class="accordion-button collapsed bg-heading2" type="button" data-bs-toggle="collapse" data-bs-target="#accordion-1 .item-2" aria-expanded="false" aria-controls="accordion-1 .item-2">City</button></h2> <h2 class="accordion-header" role="tab"><button class="accordion-button bg-heading2" type="button" data-bs-toggle="collapse" data-bs-target="#accordion-1 .item-2" aria-expanded="true" aria-controls="accordion-1 .item-2">City</button></h2>
<div class="accordion-collapse collapse item-2" role="tabpanel" data-bs-parent="#accordion-1"> <div class="accordion-collapse collapse show item-2" role="tabpanel" data-bs-parent="#accordion-1">
<div class="accordion-body"> <div class="accordion-body">
<ul id="citylist"></ul> <div class="col w-100 h-100">
<div class="row">
<div class="col">
<ul id="citylist"></ul>
</div>
</div>
<div class="row">
<div class="col"><button class="btn btn-primary w-100 h-100 ms-1 me-1" id="city_selectall" type="button">Select All</button></div>
<div class="col"><button class="btn btn-primary w-100 h-100 ms-1 me-1" id="city_clearall" type="button">Clear All</button></div>
</div>
</div>
</div> </div>
</div> </div>
</div> </div>
@@ -181,7 +201,15 @@
<h4 class="modal-title">Broadcast Zones Selection</h4> <h4 class="modal-title">Broadcast Zones Selection</h4>
</div> </div>
<div class="modal-body bg-modal-body"> <div class="modal-body bg-modal-body">
<ul id="broadcastzonelist"></ul> <div class="row">
<div class="col">
<ul id="broadcastzonelist"></ul>
</div>
</div>
<div class="row">
<div class="col"><button class="btn btn-primary w-100 h-100 ms-1 me-1" id="bzone_selectall" type="button">Select All</button></div>
<div class="col"><button class="btn btn-primary" id="bzone_clearall" type="button">Clear All</button></div>
</div>
</div> </div>
<div class="modal-footer"><button class="btn btn-round-basic color-edit class25" id="broadcastzoneselectionclose" type="button" data-bs-dismiss="modal">Close</button><button class="btn btn-round-basic color-add class25" id="broadcastzoneselectionsave" type="button">Save</button></div> <div class="modal-footer"><button class="btn btn-round-basic color-edit class25" id="broadcastzoneselectionclose" type="button" data-bs-dismiss="modal">Close</button><button class="btn btn-round-basic color-add class25" id="broadcastzoneselectionsave" type="button">Save</button></div>
</div> </div>
@@ -194,7 +222,15 @@
<h4 class="modal-title">Message Bank Selection</h4> <h4 class="modal-title">Message Bank Selection</h4>
</div> </div>
<div class="modal-body bg-modal-body"> <div class="modal-body bg-modal-body">
<ul id="messagebanklist"></ul> <div class="row">
<div class="col">
<ul id="messagebanklist"></ul>
</div>
</div>
<div class="row">
<div class="col"><button class="btn btn-primary w-100 h-100 ms-1 me-1" id="mbank_selectall" type="button">Select All</button></div>
<div class="col"><button class="btn btn-primary w-100 h-100 ms-1 me-1" id="mbank_clearall" type="button">Clear All</button></div>
</div>
</div> </div>
<div class="modal-footer"><button class="btn btn-round-basic color-edit class25" id="messagebankselectionclose" type="button" data-bs-dismiss="modal">Close</button><button class="btn btn-round-basic color-add class25" id="messagebankselectionsave" type="button">Save</button></div> <div class="modal-footer"><button class="btn btn-round-basic color-edit class25" id="messagebankselectionclose" type="button" data-bs-dismiss="modal">Close</button><button class="btn btn-round-basic color-add class25" id="messagebankselectionsave" type="button">Save</button></div>
</div> </div>

View File

@@ -0,0 +1,3 @@
Manifest-Version: 1.0
Main-Class: MainKt

View File

@@ -1,4 +1,5 @@
import audio.AudioPlayer import audio.AudioPlayer
import audio.ContentCache import audio.ContentCache
import audio.TCPReceiver import audio.TCPReceiver
import audio.UDPReceiver import audio.UDPReceiver
@@ -7,6 +8,7 @@ import barix.TCP_Barix_Command_Server
import codes.Somecodes import codes.Somecodes
import codes.configFile import codes.configFile
import codes.configKeys import codes.configKeys
import com.sun.jna.Native
import com.sun.jna.Platform import com.sun.jna.Platform
import commandServer.TCP_Android_Command_Server import commandServer.TCP_Android_Command_Server
import content.Category import content.Category
@@ -24,10 +26,12 @@ import org.tinylog.provider.ProviderRegistry
import oshi.util.GlobalConfig import oshi.util.GlobalConfig
import securedonglex.DongleChecker import securedonglex.DongleChecker
import web.WebApp import web.WebApp
import java.io.File
import java.nio.file.Files import java.nio.file.Files
import java.nio.file.Paths import java.nio.file.Paths
import kotlin.concurrent.fixedRateTimer import kotlin.concurrent.fixedRateTimer
import kotlin.io.path.absolutePathString import kotlin.io.path.absolutePathString
import kotlin.io.path.exists
import kotlin.system.exitProcess import kotlin.system.exitProcess
lateinit var db: MariaDB lateinit var db: MariaDB
@@ -35,7 +39,7 @@ lateinit var audioPlayer: AudioPlayer
val StreamerOutputs: MutableMap<String, BarixConnection> = HashMap() val StreamerOutputs: MutableMap<String, BarixConnection> = HashMap()
lateinit var udpreceiver: UDPReceiver lateinit var udpreceiver: UDPReceiver
lateinit var tcpreceiver: TCPReceiver lateinit var tcpreceiver: TCPReceiver
const val version = "0.0.17 (26/01/2026)" const val version = "0.0.23 (29/01/2026)"
// AAS 64 channels // AAS 64 channels
const val max_channel = 64 const val max_channel = 64
@@ -73,45 +77,55 @@ fun folder_preparation(){
} }
private fun Extract_Libraries() {
// extract from source root folder to current user dir
val libs = listOf("bass", "bassenc", "bassenc_mp3","bassenc_ogg","bassenc_opus","bassmix","bassopus","sdx")
try{
val targetfolder = File(Somecodes.current_directory)
Logger.info {"target to extract libraries : $targetfolder"}
libs.forEach { ff ->
val x = Native.extractFromResourcePath(ff)
val y = System.mapLibraryName(ff)
val z = x.copyTo(targetfolder.resolve(y),overwrite = true)
Logger.info {"Extracted libraries : $z"}
}
} catch (e : Exception){
Logger.error { "Error extracting libraries, msg : ${e.message}" }
}
}
/** /**
* Extract necessary wav files from classpath to soundbank directory * Extract necessary wav files from classpath to soundbank directory
* and Load them * and Load them
*/ */
fun files_preparation(){ fun files_preparation(){
val list = listOf("chimeup.wav", "chimedown.wav", "silence1s.wav", "silencehalf.wav") val list = listOf("chimeup.wav", "chimedown.wav", "silence1s.wav", "silencehalf.wav")
list.forEach { list.forEach { ff ->
Somecodes.ExtractFilesFromClassPath("/$it", Somecodes.Soundbank_directory) Somecodes.extractWav(ff)
val pp = Somecodes.Soundbank_directory.resolve(it) val fd = Somecodes.Soundbank_directory.resolve(ff)
if (Files.isRegularFile(pp)){ if (fd.exists()){
val afi = audioPlayer.LoadAudioFile(pp.absolutePathString()) Logger.info{"File ${fd.absolutePathString()} found, processing to content cache" }
val afi = audioPlayer.LoadAudioFile(fd.absolutePathString())
if (afi.isValid()){ if (afi.isValid()){
Logger.info { "Common audio $it loaded from ${pp.toAbsolutePath()}" } val key = Somecodes.FilenameWithoutExtension(fd.toFile())
val key = it.substring(0, it.length - 4) // buang .wav contentCache.addAudioFile(Somecodes.FilenameWithoutExtension(fd.toFile()), afi)
contentCache.addAudioFile(key, afi) Logger.info{"Loaded file ${fd.absolutePathString()} to content cache as $key" }
} else { } else {
Logger.error { "Failed to load common audio $it from ${pp.toAbsolutePath()}" } Logger.error{"Failed to load file ${fd.absolutePathString()} to content cache" }
} }
} else { } else {
Logger.error { "Common audio $it not found at ${pp.toAbsolutePath()}" } Logger.error{"File ${fd.absolutePathString()} not found after extraction" }
} }
} }
} }
lateinit var config : configFile lateinit var config : configFile
val sdx = DongleChecker() //val sdx = DongleChecker()
// Application start here // Application start here
fun main() { fun main() {
if (!sdx.CheckDongle()){
Logger.error { "Dongle check failed. Application will exit." }
exitProcess(1)
} else {
sdx.startChecking {
Logger.error { "Dongle removed. Application will exit." }
exitProcess(1)
sdx.stopChecking()
}
}
@@ -124,6 +138,17 @@ fun main() {
config = configFile() config = configFile()
folder_preparation() folder_preparation()
Extract_Libraries()
// if (!sdx.CheckDongle()){
// Logger.error { "Dongle check failed. Application will exit." }
// exitProcess(1)
// } else {
// sdx.startChecking {
// Logger.error { "Dongle removed. Application will exit." }
// exitProcess(1)
// }
// }
audioPlayer = AudioPlayer(44100) // 44100 Hz sampling rate audioPlayer = AudioPlayer(44100) // 44100 Hz sampling rate
audioPlayer.InitAudio(1) audioPlayer.InitAudio(1)
@@ -262,7 +287,7 @@ fun main() {
StreamerOutputs.values.forEach { it.close() } StreamerOutputs.values.forEach { it.close() }
audioPlayer.Close() audioPlayer.Close()
db.close() db.close()
sdx.stopChecking() //sdx.stopChecking()
Logger.info { "All services stopped, exiting application." } Logger.info { "All services stopped, exiting application." }
ProviderRegistry.getLoggingProvider().shutdown() ProviderRegistry.getLoggingProvider().shutdown()

View File

@@ -99,7 +99,7 @@ class MainExtension01 {
*/ */
fun Get_Barix_Connection_by_ZoneName(zonename: String) : BarixConnection? { fun Get_Barix_Connection_by_ZoneName(zonename: String) : BarixConnection? {
if (ValidString(zonename)){ if (ValidString(zonename)){
val bz = db.broadcastDB.List.find{ it.description == zonename } val bz = db.broadcastDB.List.find{ it.description.equals(zonename,true) }
val sc = if (bz!=null) db.soundchannelDB.List.find { it.channel == bz.SoundChannel } else null val sc = if (bz!=null) db.soundchannelDB.List.find { it.channel == bz.SoundChannel } else null
val ip = sc?.ip ?: "" val ip = sc?.ip ?: ""
if (ValidIPV4(ip)){ if (ValidIPV4(ip)){
@@ -165,7 +165,7 @@ class MainExtension01 {
match.forEach { match.forEach {
mm -> mm ->
if (IsNumber(mm.value)) { if (IsNumber(mm.value)) {
val num =sb.firstOrNull { s1 -> s1.Category == Category.AlphabetNumeric.name && s1.TAG == "N${mm.value}" } val num =sb.firstOrNull { s1 -> s1.Category.equals(Category.AlphabetNumeric.name, true) && s1.TAG.equals("N${mm.value}", true) }
if (num!=null){ if (num!=null){
if (ValidFile(num.Path)){ if (ValidFile(num.Path)){
result.add(num.Path) result.add(num.Path)
@@ -173,7 +173,7 @@ class MainExtension01 {
} }
} else if (IsAlphabethic(mm.value)) { } else if (IsAlphabethic(mm.value)) {
val alp = val alp =
sb.firstOrNull { s1 -> s1.Category == Category.AlphabetNumeric.name && s1.TAG == mm.value } sb.firstOrNull { s1 -> s1.Category.equals(Category.AlphabetNumeric.name, true) && s1.TAG.equals(mm.value,true) }
if (alp != null) { if (alp != null) {
if (ValidFile(alp.Path)) { if (ValidFile(alp.Path)) {
result.add(alp.Path) result.add(alp.Path)
@@ -191,7 +191,7 @@ class MainExtension01 {
fun Get_Soundbank_Hour_Minute(sb: List<Soundbank>, value: Int) : String { fun Get_Soundbank_Hour_Minute(sb: List<Soundbank>, value: Int) : String {
if (value in 0..59){ if (value in 0..59){
val tag = if (value<10) "N0${value}" else "N${value}" val tag = if (value<10) "N0${value}" else "N${value}"
val hm = sb.firstOrNull { it.Category == Category.AlphabetNumeric.name && it.TAG == tag } val hm = sb.firstOrNull { it.Category.equals(Category.AlphabetNumeric.name,true) && it.TAG.equals(tag, true) }
if (hm!=null){ if (hm!=null){
if (ValidFile(hm.Path)) return hm.Path if (ValidFile(hm.Path)) return hm.Path
} }
@@ -265,7 +265,7 @@ class MainExtension01 {
val value = variables["AL"].orEmpty() val value = variables["AL"].orEmpty()
if (ValidString(value)) { if (ValidString(value)) {
val airplane = val airplane =
sb.firstOrNull { it.Category == Category.Airplane_Name.name && it.TAG == value } sb.firstOrNull { it.Category.equals(Category.Airplane_Name.name,true) && it.TAG.equals(value,true) }
if (airplane != null) { if (airplane != null) {
if (ValidFile(airplane.Path)) { if (ValidFile(airplane.Path)) {
files.add(airplane.Path) files.add(airplane.Path)
@@ -288,7 +288,7 @@ class MainExtension01 {
val alcode = variables["AL"].orEmpty() val alcode = variables["AL"].orEmpty()
val fncode = variables["FLNUM"].orEmpty() val fncode = variables["FLNUM"].orEmpty()
if (ValidString(alcode) && ValidString(fncode)) { if (ValidString(alcode) && ValidString(fncode)) {
val val1 = sb.firstOrNull { it.Category == Category.Airline_Code.name && it.TAG == alcode } val val1 = sb.firstOrNull { it.Category.equals(Category.Airline_Code.name,true) && it.TAG.equals(alcode, true) }
val val2 = Get_Soundbank_AlpabethNumeric(sb, fncode) val val2 = Get_Soundbank_AlpabethNumeric(sb, fncode)
if (val1 != null) { if (val1 != null) {
if (ValidFile(val1.Path)) { if (ValidFile(val1.Path)) {
@@ -360,7 +360,7 @@ class MainExtension01 {
val values = variables["CITY"].orEmpty().split(";").map { it.trim() }.filter { ValidString(it) } val values = variables["CITY"].orEmpty().split(";").map { it.trim() }.filter { ValidString(it) }
if (values.isNotEmpty()) { if (values.isNotEmpty()) {
values.forEach { vv -> values.forEach { vv ->
val city = sb.firstOrNull { it.Category == Category.City.name && it.TAG == vv } val city = sb.firstOrNull { it.Category.equals(Category.City.name,true) && it.TAG.equals(vv,true) }
if (city != null) { if (city != null) {
if (ValidFile(city.Path)) { if (ValidFile(city.Path)) {
files.add(city.Path) files.add(city.Path)
@@ -380,7 +380,7 @@ class MainExtension01 {
"[PLACES]" -> { "[PLACES]" -> {
val value = variables["PLACES"].orEmpty() val value = variables["PLACES"].orEmpty()
if (ValidString(value)) { if (ValidString(value)) {
val places = sb.firstOrNull { it.Category == Category.Places.name && it.TAG == value } val places = sb.firstOrNull { it.Category.equals(Category.Places.name,true) && it.TAG.equals(value,true) }
if (places != null) { if (places != null) {
if (ValidFile(places.Path)) { if (ValidFile(places.Path)) {
files.add(places.Path) files.add(places.Path)
@@ -434,7 +434,7 @@ class MainExtension01 {
"[SHALAT]" -> { "[SHALAT]" -> {
val value = variables["SHALAT"].orEmpty() val value = variables["SHALAT"].orEmpty()
if (ValidString(value)) { if (ValidString(value)) {
val shalat = sb.firstOrNull { it.Category == Category.Shalat.name && it.TAG == value } val shalat = sb.firstOrNull { it.Category.equals(Category.Shalat.name,true) && it.TAG.equals(value,true) }
if (shalat != null) { if (shalat != null) {
if (ValidFile(shalat.Path)) { if (ValidFile(shalat.Path)) {
files.add(shalat.Path) files.add(shalat.Path)
@@ -496,7 +496,7 @@ class MainExtension01 {
"[REASON]" -> { "[REASON]" -> {
val value = variables["REASON"].orEmpty() val value = variables["REASON"].orEmpty()
if (ValidString(value)) { if (ValidString(value)) {
val reason = sb.firstOrNull { it.Category == Category.Reason.name && it.TAG == value } val reason = sb.firstOrNull { it.Category.equals(Category.Reason.name,true) && it.TAG.equals(value,true) }
if (reason != null) { if (reason != null) {
if (ValidFile(reason.Path)) { if (ValidFile(reason.Path)) {
files.add(reason.Path) files.add(reason.Path)
@@ -518,7 +518,7 @@ class MainExtension01 {
"[PROCEDURE]" -> { "[PROCEDURE]" -> {
val value = variables["PROCEDURE"].orEmpty() val value = variables["PROCEDURE"].orEmpty()
if (ValidString(value)) { if (ValidString(value)) {
val procedure = sb.firstOrNull { it.Category == Category.Procedure.name && it.TAG == value } val procedure = sb.firstOrNull { it.Category.equals(Category.Procedure.name, true) && it.TAG.equals(value, true) }
if (procedure != null) { if (procedure != null) {
if (ValidFile(procedure.Path)) { if (ValidFile(procedure.Path)) {
files.add(procedure.Path) files.add(procedure.Path)
@@ -539,7 +539,7 @@ class MainExtension01 {
else -> { else -> {
// Phrase // Phrase
val phrase = sb.firstOrNull { it.Category == Category.Phrase.name && it.TAG == _tag } val phrase = sb.firstOrNull { it.Category.equals(Category.Phrase.name,true) && it.TAG.equals(_tag, true) }
if (phrase != null) { if (phrase != null) {
if (ValidFile(phrase.Path)) { if (ValidFile(phrase.Path)) {
files.add(phrase.Path) files.add(phrase.Path)
@@ -563,7 +563,7 @@ class MainExtension01 {
fun Read_Queue_Paging() : Boolean{ fun Read_Queue_Paging() : Boolean{
db.queuepagingDB.Get() db.queuepagingDB.Get()
val list = db.queuepagingDB.List val list = db.queuepagingDB.List
.filter { it.Type=="PAGING" } .filter { it.Type.equals("PAGING",true) }
list.forEach { qp -> list.forEach { qp ->
//println("Processing $qp") //println("Processing $qp")
@@ -633,7 +633,7 @@ class MainExtension01 {
fun Read_Queue_Shalat() : Boolean{ fun Read_Queue_Shalat() : Boolean{
db.queuepagingDB.Get() db.queuepagingDB.Get()
val list = db.queuepagingDB.List val list = db.queuepagingDB.List
.filter { it.Type=="SHALAT" } .filter { it.Type.equals("SHALAT",true) }
list.forEach { qp -> list.forEach { qp ->
//println("Processing $qp") //println("Processing $qp")
if (qp.BroadcastZones.isNotBlank()){ if (qp.BroadcastZones.isNotBlank()){
@@ -747,7 +747,7 @@ class MainExtension01 {
fun Read_Queue_Timer() : Boolean{ fun Read_Queue_Timer() : Boolean{
db.queuetableDB.Get() db.queuetableDB.Get()
val list = db.queuetableDB.List.filter { it.Type=="TIMER" } val list = db.queuetableDB.List.filter { it.Type.equals("TIMER",true) }
list.forEach { qa -> list.forEach { qa ->
//println("Processing $qa") //println("Processing $qa")
if (qa.BroadcastZones.isNotEmpty()){ if (qa.BroadcastZones.isNotEmpty()){
@@ -852,7 +852,7 @@ class MainExtension01 {
fun Activate_Relays(zz: List<String>){ fun Activate_Relays(zz: List<String>){
zz.forEach { zonename -> zz.forEach { zonename ->
val bz = db.broadcastDB.List.find { it.description == zonename } val bz = db.broadcastDB.List.find { it.description.equals(zonename,true) }
if (bz!=null){ if (bz!=null){
val bc = Get_Barix_Connection_by_ZoneName(zonename) val bc = Get_Barix_Connection_by_ZoneName(zonename)
if (bc!=null){ if (bc!=null){
@@ -872,7 +872,7 @@ class MainExtension01 {
fun Deactivate_Relays(zz: List<String>){ fun Deactivate_Relays(zz: List<String>){
zz.forEach { zonename -> zz.forEach { zonename ->
val bz = db.broadcastDB.List.find { it.description == zonename } val bz = db.broadcastDB.List.find { it.description.equals(zonename,true) }
if (bz!=null){ if (bz!=null){
val bc = Get_Barix_Connection_by_ZoneName(zonename) val bc = Get_Barix_Connection_by_ZoneName(zonename)
bc?.DeactivateRelay() bc?.DeactivateRelay()
@@ -886,7 +886,7 @@ class MainExtension01 {
*/ */
fun Read_Queue_Soundbank() : Boolean{ fun Read_Queue_Soundbank() : Boolean{
db.queuetableDB.Get() db.queuetableDB.Get()
val list = db.queuetableDB.List.filter { it.Type=="SOUNDBANK" } val list = db.queuetableDB.List.filter { it.Type.equals("SOUNDBANK",true) }
list.forEach { qa -> list.forEach { qa ->
//println("Processing $qa") //println("Processing $qa")
if (qa.BroadcastZones.isNotEmpty()){ if (qa.BroadcastZones.isNotEmpty()){
@@ -1045,7 +1045,7 @@ class MainExtension01 {
if (localtime.second != 0) return if (localtime.second != 0) return
val timestring = timeformat2.format(localtime) val timestring = timeformat2.format(localtime)
val sch = db.scheduleDB.List.filter { val sch = db.scheduleDB.List.filter {
it.Time == timestring && it.Enable it.Time.equals(timestring,true) && it.Enable
} }
// tidak ada schedule dengan time sekarang dan enable=true // tidak ada schedule dengan time sekarang dan enable=true
if (sch.isEmpty()) return if (sch.isEmpty()) return
@@ -1054,7 +1054,7 @@ class MainExtension01 {
val ddmmyyyy = dateformat1.format(localdate) val ddmmyyyy = dateformat1.format(localdate)
// check special date dulu // check special date dulu
val specialdate = sch.find { val specialdate = sch.find {
it.Day == ddmmyyyy it.Day.equals(ddmmyyyy,true)
} }
if (specialdate != null) { if (specialdate != null) {
val qt = QueueTable( val qt = QueueTable(

View File

@@ -1,13 +1,15 @@
package audio; package audio;
import codes.Somecodes;
import com.sun.jna.*; import com.sun.jna.*;
@SuppressWarnings("unused") @SuppressWarnings({"unused"})
public interface Bass extends Library { public interface Bass extends Library {
Bass Instance = (Bass) Native.load("bass", Bass.class);
Bass Instance = (Bass) Native.load(Somecodes.Companion.LibraryFullPath("bass"), Bass.class);
int BASSVERSION = 0x204; // API version int BASSVERSION = 0x204; // API version
String BASSVERSIONTEXT = "2.4"; String BASSVERSIONTEXT = "2.4";

View File

@@ -1,11 +1,12 @@
package audio; package audio;
import codes.Somecodes;
import com.sun.jna.*; import com.sun.jna.*;
@SuppressWarnings("unused") @SuppressWarnings({"unused"})
public interface BassEnc extends Library { public interface BassEnc extends Library {
BassEnc Instance = (BassEnc) Native.load("bassenc", BassEnc.class); BassEnc Instance = (BassEnc) Native.load(Somecodes.Companion.LibraryFullPath("bassenc"), BassEnc.class);
// Additional error codes returned by BASS_ErrorGetCode // Additional error codes returned by BASS_ErrorGetCode
int BASS_ERROR_CAST_DENIED = 2100; // access denied (invalid password) int BASS_ERROR_CAST_DENIED = 2100; // access denied (invalid password)

View File

@@ -1,11 +1,13 @@
package audio; package audio;
import codes.Somecodes;
import com.sun.jna.Library; import com.sun.jna.Library;
import com.sun.jna.Native;
@SuppressWarnings("unused") @SuppressWarnings({"unused"})
public interface BassEncMP3 extends Library { public interface BassEncMP3 extends Library {
BassEncMP3 Instance = (BassEncMP3) com.sun.jna.Native.load("bassenc_mp3", BassEncMP3.class); BassEncMP3 Instance = (BassEncMP3) Native.load(Somecodes.Companion.LibraryFullPath("bassenc_mp3"), BassEncMP3.class);
int BASS_Encode_MP3_GetVersion(); int BASS_Encode_MP3_GetVersion();
int BASS_Encode_MP3_Start(int handle, String options, int flags, BassEnc.ENCODEPROCEX proc, Object user); int BASS_Encode_MP3_Start(int handle, String options, int flags, BassEnc.ENCODEPROCEX proc, Object user);
int BASS_Encode_MP3_StartFile(int handle, String options, int flags, String filename); int BASS_Encode_MP3_StartFile(int handle, String options, int flags, String filename);

View File

@@ -1,11 +1,13 @@
package audio; package audio;
import codes.Somecodes;
import com.sun.jna.Library; import com.sun.jna.Library;
import com.sun.jna.Native;
@SuppressWarnings("unused") @SuppressWarnings({"unused"})
public interface BassEncOGG extends Library { public interface BassEncOGG extends Library {
BassEncOGG Instance = (BassEncOGG) com.sun.jna.Native.load("bassenc_ogg", BassEncOGG.class); BassEncOGG Instance = (BassEncOGG) Native.load(Somecodes.Companion.LibraryFullPath("bassenc_ogg"), BassEncOGG.class);
int BASS_ENCODE_OGG_RESET = 0x1000000; int BASS_ENCODE_OGG_RESET = 0x1000000;
int BASS_Encode_OGG_GetVersion(); int BASS_Encode_OGG_GetVersion();
int BASS_Encode_OGG_Start(int handle, String options, int flags, BassEnc.ENCODEPROC proc, Object user); int BASS_Encode_OGG_Start(int handle, String options, int flags, BassEnc.ENCODEPROC proc, Object user);

View File

@@ -1,10 +1,12 @@
package audio; package audio;
import codes.Somecodes;
import com.sun.jna.Library; import com.sun.jna.Library;
import com.sun.jna.Native;
@SuppressWarnings("unused") @SuppressWarnings({"unused"})
public interface BassEncOpus extends Library { public interface BassEncOpus extends Library {
BassEncOpus Instance = (BassEncOpus) com.sun.jna.Native.load("bassenc_opus", BassEncOpus.class); BassEncOpus Instance = (BassEncOpus) Native.load(Somecodes.Companion.LibraryFullPath("bassenc_opus"), BassEncOpus.class);
int BASS_ENCODE_OPUS_RESET = 0x1000000; int BASS_ENCODE_OPUS_RESET = 0x1000000;
int BASS_ENCODE_OPUS_CTLONLY = 0x2000000; int BASS_ENCODE_OPUS_CTLONLY = 0x2000000;

View File

@@ -1,13 +1,14 @@
package audio; package audio;
import codes.Somecodes;
import com.sun.jna.Library; import com.sun.jna.Library;
import com.sun.jna.Native; import com.sun.jna.Native;
import com.sun.jna.Pointer; import com.sun.jna.Pointer;
@SuppressWarnings("unused") @SuppressWarnings({"unused"})
public interface BassMix extends Library { public interface BassMix extends Library {
BassMix Instance = (BassMix) Native.load("bassmix", BassMix.class); BassMix Instance = (BassMix) Native.load(Somecodes.Companion.LibraryFullPath("bassmix"), BassMix.class);
// Envelope node // Envelope node
class BASS_MIXER_NODE { class BASS_MIXER_NODE {

View File

@@ -1,12 +1,13 @@
package audio; package audio;
import codes.Somecodes;
import com.sun.jna.Library; import com.sun.jna.Library;
import com.sun.jna.Native; import com.sun.jna.Native;
import com.sun.jna.Pointer; import com.sun.jna.Pointer;
@SuppressWarnings("unused") @SuppressWarnings({"unused"})
public interface BassOpus extends Library { public interface BassOpus extends Library {
BassOpus Instance = (BassOpus) Native.load("bassopus", BassOpus.class); BassOpus Instance = (BassOpus) Native.load(Somecodes.Companion.LibraryFullPath("bassopus"), BassOpus.class);
// BASS_CHANNELINFO type // BASS_CHANNELINFO type
int BASS_CTYPE_STREAM_OPUS = 0x11200; int BASS_CTYPE_STREAM_OPUS = 0x11200;

View File

@@ -18,12 +18,15 @@ import oshi.hardware.GlobalMemory
import oshi.hardware.NetworkIF import oshi.hardware.NetworkIF
import oshi.hardware.Sensors import oshi.hardware.Sensors
import oshi.software.os.OperatingSystem import oshi.software.os.OperatingSystem
import java.io.File
import java.nio.file.Files import java.nio.file.Files
import java.nio.file.Path import java.nio.file.Path
import java.nio.file.StandardCopyOption
import java.time.LocalDateTime import java.time.LocalDateTime
import java.time.format.DateTimeFormatter import java.time.format.DateTimeFormatter
import java.util.function.BiConsumer import java.util.function.BiConsumer
import java.util.function.Consumer import java.util.function.Consumer
import kotlin.io.path.exists
import kotlin.io.path.name import kotlin.io.path.name
@@ -193,6 +196,35 @@ class Somecodes {
return byteArray return byteArray
} }
fun LibraryFullPath(libname: String) : String{
val ff = File(current_directory, System.mapLibraryName(libname))
return if (ff.isFile) ff.absolutePath else ""
}
fun extractWav(filename: String) : Boolean {
val resourcePath = "/$filename"
try{
val input = object {}.javaClass.getResourceAsStream(resourcePath)
?: error("Resource not found: $resourcePath")
val target = Soundbank_directory.resolve(filename) // current working directory
if (target.exists()) {
Logger.info {"File $filename already exists as $target, skipping extraction." }
return true
}
input.use {
Files.copy(it, target, StandardCopyOption.REPLACE_EXISTING)
}
Logger.info {"File $filename extracted as $target"}
return true
} catch (e : Exception){
Logger.error { "Error copying file $filename: ${e.message}" }
return false
}
}
fun ExtractFilesFromClassPath(resourcePath: String, outputDir: Path) { fun ExtractFilesFromClassPath(resourcePath: String, outputDir: Path) {
try { try {
val resource = Somecodes::class.java.getResource(resourcePath) val resource = Somecodes::class.java.getResource(resourcePath)
@@ -466,6 +498,16 @@ class Somecodes {
return false return false
} }
fun FilenameWithoutExtension(ff : File) : String{
val name = ff.name
val lastDotIndex = name.lastIndexOf('.')
return if (lastDotIndex != -1) {
name.substring(0, lastDotIndex)
} else {
name
}
}
/** /**
* Check if a string is a valid file path and the file exists. * Check if a string is a valid file path and the file exists.
* @param value The string to check. * @param value The string to check.
@@ -473,7 +515,8 @@ class Somecodes {
*/ */
fun ValidFile(value : String) : Boolean { fun ValidFile(value : String) : Boolean {
if (value.isNotBlank()){ if (value.isNotBlank()){
return ValidFile(Path.of(value)) val ff = File(value)
return ff.isFile
} }
return false return false
} }

View File

@@ -86,6 +86,9 @@ class WebApp(val listenPort: Int, var userlist: List<Pair<String, String>>, val
config.staticFiles.add("/webpage") config.staticFiles.add("/webpage")
config.jsonMapper(JavalinJackson(jacksonObjectMapper())) config.jsonMapper(JavalinJackson(jacksonObjectMapper()))
config.router.apiBuilder { config.router.apiBuilder {
before {
//Logger.info {"${it.ip()} connecting ${it.method()} to ${it.path()}"}
}
path("/") { path("/") {
get { ctx -> get { ctx ->
// Serve the main page // Serve the main page
@@ -2302,6 +2305,7 @@ class WebApp(val listenPort: Int, var userlist: List<Pair<String, String>>, val
} }
} }
}.start(listenPort) }.start(listenPort)
} }
private fun Start_SemiAutoServer() { private fun Start_SemiAutoServer() {
@@ -2311,6 +2315,9 @@ class WebApp(val listenPort: Int, var userlist: List<Pair<String, String>>, val
config.staticFiles.add("/semiauto") config.staticFiles.add("/semiauto")
config.jsonMapper(JavalinJackson(jacksonObjectMapper())) config.jsonMapper(JavalinJackson(jacksonObjectMapper()))
config.router.apiBuilder { config.router.apiBuilder {
before{
//Logger.info{"${it.ip()} method ${it.method()} connect to ${it.path()}"}
}
path("/") { path("/") {
get { get {
it.cookie("semiauto-user", "") it.cookie("semiauto-user", "")