Compare commits
No commits in common. "83e3c53ebc9c283d301512cdc6615f50777da508" and "59cad38f74fe84398b04ccef95c13635f803b870" have entirely different histories.
83e3c53ebc
...
59cad38f74
|
|
@ -1,2 +0,0 @@
|
||||||
class MIA { //TODO: Semantic Kernel Class
|
|
||||||
}
|
|
||||||
|
|
@ -1,61 +0,0 @@
|
||||||
import javax.sound.sampled.AudioFormat
|
|
||||||
import javax.sound.sampled.AudioSystem
|
|
||||||
import javax.sound.sampled.DataLine
|
|
||||||
import javax.sound.sampled.TargetDataLine
|
|
||||||
/**
|
|
||||||
* TODO: Documentation
|
|
||||||
*/
|
|
||||||
class Microphone {
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
private val source = getSource()
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
private val audioFormat = getFormat()
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
fun startCapture() {
|
|
||||||
source.start()
|
|
||||||
//TODO: Start processing loop in new coroutine and check if it could be moved into own file
|
|
||||||
}
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
fun stopCapture() {
|
|
||||||
source.stop()
|
|
||||||
}
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
fun closeSource() {
|
|
||||||
source.close()
|
|
||||||
}
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
private fun getFormat(): AudioFormat {
|
|
||||||
return AudioFormat( //TODO: Get format settings from user settings
|
|
||||||
16000.0f, // 16000 Required
|
|
||||||
16,
|
|
||||||
2,
|
|
||||||
true,
|
|
||||||
true
|
|
||||||
)
|
|
||||||
}
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
private fun getSource(): TargetDataLine {
|
|
||||||
val info = DataLine.Info(
|
|
||||||
TargetDataLine::class.java,
|
|
||||||
audioFormat
|
|
||||||
)
|
|
||||||
val source = AudioSystem.getLine(info) as TargetDataLine
|
|
||||||
source.open(audioFormat)
|
|
||||||
|
|
||||||
return source
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
@ -1,39 +0,0 @@
|
||||||
import org.vosk.Model
|
|
||||||
import org.vosk.Recognizer
|
|
||||||
import java.nio.file.Paths
|
|
||||||
/**
|
|
||||||
* TODO: Documentation
|
|
||||||
*/
|
|
||||||
class STT {
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
private val model = Model(getModelPath())
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
private val recognizer = Recognizer(model, 16000.0f)
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
fun parseBuffer(buffer: ByteArray, audioBytes: Int): String? {
|
|
||||||
return if (recognizer.acceptWaveForm(buffer, audioBytes)) {
|
|
||||||
recognizer.result
|
|
||||||
} else {
|
|
||||||
recognizer.partialResult
|
|
||||||
}
|
|
||||||
}
|
|
||||||
fun closeModel() {
|
|
||||||
recognizer.close()
|
|
||||||
}
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
private fun getModelPath(): String {
|
|
||||||
return Paths.get(
|
|
||||||
javaClass.getResource("STT-model")!!.toURI()
|
|
||||||
).toFile().absolutePath
|
|
||||||
}
|
|
||||||
|
|
||||||
//TODO: Install model into dir from resource link
|
|
||||||
}
|
|
||||||
|
|
@ -1,7 +0,0 @@
|
||||||
package window_control
|
|
||||||
|
|
||||||
enum class OS {
|
|
||||||
Windows,
|
|
||||||
Mac,
|
|
||||||
Linux
|
|
||||||
}
|
|
||||||
|
|
@ -1,112 +0,0 @@
|
||||||
package window_control
|
|
||||||
|
|
||||||
import com.sun.jna.Library
|
|
||||||
import com.sun.jna.Native
|
|
||||||
import com.sun.jna.platform.win32.WinDef
|
|
||||||
import com.sun.jna.win32.W32APIOptions
|
|
||||||
import java.awt.Point
|
|
||||||
import java.awt.Robot
|
|
||||||
import java.awt.event.KeyEvent
|
|
||||||
|
|
||||||
class WindowController { //TODO: Class that controls program window
|
|
||||||
private val os = OS.valueOf(System.getProperty("os.name"))
|
|
||||||
private val inputController = Robot()
|
|
||||||
|
|
||||||
fun setActiveWindow(windowName: String) {
|
|
||||||
when (os) {
|
|
||||||
OS.Windows -> activateWindowsWindow(windowName)
|
|
||||||
OS.Mac -> activateMacWindow(windowName)
|
|
||||||
OS.Linux -> activateLinuxWindow(windowName)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fun sendKeyPresses(keyCodes: Array<Int>) {
|
|
||||||
keyCodes.iterator().forEach { keyCode ->
|
|
||||||
inputController.keyPress(keyCode)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
fun sendKeyReleases(keyCodes: Array<Int>) {
|
|
||||||
keyCodes.iterator().forEach { keyCode ->
|
|
||||||
inputController.keyRelease(keyCode)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
fun sendKeyStrokes(keyCodes: Array<Int>, delay: Int?) { //TODO: Create KeyList Class
|
|
||||||
keyCodes.iterator().forEach { keyCode ->
|
|
||||||
sendKeyPresses(arrayOf(keyCode))
|
|
||||||
inputController.delay(delay!!)
|
|
||||||
sendKeyReleases(arrayOf(keyCode))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fun sendMultiKeyStrokes(commands: Array<Array<Int>>, delay: Int?) { //TODO: Create MultiKeyList Class
|
|
||||||
commands.iterator().forEach { command ->
|
|
||||||
sendMousePresses(command)
|
|
||||||
inputController.delay(delay!!)
|
|
||||||
sendMouseReleases(command)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fun sendMousePresses(buttonCodes: Array<Int>) { //TODO: Create ButtonList Class
|
|
||||||
buttonCodes.iterator().forEach { buttonCode ->
|
|
||||||
inputController.mousePress(buttonCode)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
fun sendMouseReleases(buttonCodes: Array<Int>) {
|
|
||||||
buttonCodes.iterator().forEach { buttonCode ->
|
|
||||||
inputController.mouseRelease(buttonCode)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
fun sendMouseLocation(location: Point) {
|
|
||||||
inputController.mouseMove(location.x, location.y)
|
|
||||||
}
|
|
||||||
fun sendMouseStrokes(buttonCodes: Array<Int>, delay: Int?) {
|
|
||||||
buttonCodes.iterator().forEach { buttonCode ->
|
|
||||||
sendMousePresses(arrayOf(buttonCode))
|
|
||||||
inputController.delay(delay!!)
|
|
||||||
sendMouseReleases(arrayOf(buttonCode))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
fun sendMouseStrokesAtLocation(buttonCodes: Array<Int>, delay: Int?, location: Point) {
|
|
||||||
sendMouseLocation(location)
|
|
||||||
buttonCodes.iterator().forEach { buttonCode ->
|
|
||||||
sendMouseStrokes(arrayOf(buttonCode), delay)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
fun sendMouseStrokesAtLocations(commands: Array<Pair<Point,Array<Int>>>, delay: Int?) {
|
|
||||||
commands.iterator().forEach { command ->
|
|
||||||
sendMouseLocation(command.first)
|
|
||||||
sendMouseStrokes(command.second, delay)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun activateWindowsWindow(windowName: String) {
|
|
||||||
val window = User32.INSTANCE.findWindow(null, windowName)
|
|
||||||
User32.INSTANCE.setActiveWindow(window)
|
|
||||||
}
|
|
||||||
private fun activateMacWindow(windowName: String) {
|
|
||||||
val command = arrayOf("osascript", "-e", "tell application \"$windowName\" to activate") //TODO: double check how this command works to ensure it works
|
|
||||||
Runtime.getRuntime().exec(command).waitFor()
|
|
||||||
}
|
|
||||||
private fun activateLinuxWindow(windowName: String) {
|
|
||||||
val xorgFlag = System.getenv("DISPLAY")
|
|
||||||
val hyprlandFlag = System.getenv("HYPRLAND_CMD") //TODO: User override of default checks, and add sway compatibility
|
|
||||||
|
|
||||||
if (hyprlandFlag != null) {
|
|
||||||
val command = arrayOf("hyprctl", "dispatch", "focuswindow", windowName) //TODO: need to check both class regex and title regex (look at hyprland wiki)
|
|
||||||
Runtime.getRuntime().exec(command).waitFor()
|
|
||||||
}
|
|
||||||
else if (xorgFlag != null) {
|
|
||||||
val command = arrayOf("xdotool", "search", "--name", windowName, "windowactivate")
|
|
||||||
Runtime.getRuntime().exec(command).waitFor()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
interface User32: Library {
|
|
||||||
companion object {
|
|
||||||
val INSTANCE: User32 = Native.load("user32", User32::class.java, W32APIOptions.DEFAULT_OPTIONS)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun findWindow(className: String?, windowName: String?): WinDef.HWND
|
|
||||||
fun setActiveWindow(window: WinDef.HWND): Boolean
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Loading…
Reference in New Issue