mirror of
https://github.com/ggerganov/ggwave.git
synced 2026-03-06 23:05:53 +08:00
ggwave : big refactoring / renaming
This commit is contained in:
@@ -45,41 +45,39 @@ void mainUpdate(void *) {
|
||||
extern "C" {
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int sendData(int textLength, const char * text, int protocolId, int volume) {
|
||||
g_ggWave->init(textLength, text, g_ggWave->getTxProtocol(protocolId), volume);
|
||||
g_ggWave->init(textLength, text, GGWave::TxProtocolId(protocolId), volume);
|
||||
return 0;
|
||||
}
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int getText(char * text) {
|
||||
std::copy(g_ggWave->getRxData().begin(), g_ggWave->getRxData().end(), text);
|
||||
std::copy(g_ggWave->rxData().begin(), g_ggWave->rxData().end(), text);
|
||||
return 0;
|
||||
}
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
float getSampleRate() { return g_ggWave->getSampleRateInp(); }
|
||||
float sampleRate() { return g_ggWave->sampleRateInp(); }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int getFramesToRecord() { return g_ggWave->getFramesToRecord(); }
|
||||
int framesToRecord() { return g_ggWave->rxFramesToRecord(); }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int getFramesLeftToRecord() { return g_ggWave->getFramesLeftToRecord(); }
|
||||
int framesLeftToRecord() { return g_ggWave->rxFramesLeftToRecord(); }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int getFramesToAnalyze() { return g_ggWave->getFramesToAnalyze(); }
|
||||
int framesToAnalyze() { return g_ggWave->rxFramesToAnalyze(); }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int getFramesLeftToAnalyze() { return g_ggWave->getFramesLeftToAnalyze(); }
|
||||
int framesLeftToAnalyze() { return g_ggWave->rxFramesLeftToAnalyze(); }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int hasDeviceOutput() { return g_devIdOut; }
|
||||
int hasDeviceOutput() { return g_devIdOut; }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int hasDeviceCapture() { return g_devIdInp; }
|
||||
int hasDeviceCapture() { return g_devIdInp; }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int doInit() {
|
||||
return g_doInit();
|
||||
}
|
||||
int doInit() { return g_doInit(); }
|
||||
}
|
||||
|
||||
void GGWave_setDefaultCaptureDeviceName(std::string name) {
|
||||
@@ -253,16 +251,16 @@ bool GGWave_mainLoop() {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (g_ggWave->hasTxData() == false) {
|
||||
if (g_ggWave->txHasData() == false) {
|
||||
SDL_PauseAudioDevice(g_devIdOut, SDL_FALSE);
|
||||
|
||||
static auto tLastNoData = std::chrono::high_resolution_clock::now();
|
||||
auto tNow = std::chrono::high_resolution_clock::now();
|
||||
|
||||
if ((int) SDL_GetQueuedAudioSize(g_devIdOut) < g_ggWave->getSamplesPerFrame()*g_ggWave->getSampleSizeBytesOut()) {
|
||||
if ((int) SDL_GetQueuedAudioSize(g_devIdOut) < g_ggWave->samplesPerFrame()*g_ggWave->sampleSizeOut()) {
|
||||
SDL_PauseAudioDevice(g_devIdInp, SDL_FALSE);
|
||||
const int nHave = (int) SDL_GetQueuedAudioSize(g_devIdInp);
|
||||
const int nNeed = g_ggWave->getSamplesPerFrame()*g_ggWave->getSampleSizeBytesInp();
|
||||
const int nNeed = g_ggWave->samplesPerFrame()*g_ggWave->sampleSizeInp();
|
||||
if (::getTime_ms(tLastNoData, tNow) > 500.0f && nHave >= nNeed) {
|
||||
static std::vector<uint8_t> dataInp(nNeed);
|
||||
SDL_DequeueAudio(g_devIdInp, dataInp.data(), nNeed);
|
||||
@@ -271,7 +269,7 @@ bool GGWave_mainLoop() {
|
||||
fprintf(stderr, "Warning: failed to decode input data!\n");
|
||||
} else {
|
||||
GGWave::TxRxData rxData;
|
||||
int n = g_ggWave->takeRxData(rxData);
|
||||
int n = g_ggWave->rxTakeData(rxData);
|
||||
if (n > 0) {
|
||||
std::time_t timestamp = std::time(nullptr);
|
||||
std::string tstr = std::asctime(std::localtime(×tamp));
|
||||
@@ -335,7 +333,8 @@ int main(int argc, char** argv) {
|
||||
printf("\n");
|
||||
#endif
|
||||
|
||||
const GGWave::TxProtocols protocols = {
|
||||
auto & protocols = GGWave::Protocols::rx();
|
||||
protocols = {
|
||||
{ "[R2T2] Normal", 64, 9, 1, 2, true, },
|
||||
{ "[R2T2] Fast", 64, 6, 1, 2, true, },
|
||||
{ "[R2T2] Fastest", 64, 3, 1, 2, true, },
|
||||
@@ -356,8 +355,6 @@ int main(int argc, char** argv) {
|
||||
return false;
|
||||
}
|
||||
|
||||
g_ggWave->setRxProtocols(protocols);
|
||||
|
||||
isInitialized = true;
|
||||
printf("Listening for payload with length = %d bytes ..\n", payloadLength);
|
||||
|
||||
|
||||
@@ -101,6 +101,7 @@
|
||||
parameters.samplesPerFrame = 512;
|
||||
parameters.sampleRateInp = context.sampleRate;
|
||||
parameters.sampleRateOut = context.sampleRate;
|
||||
parameters.operatingMode = GGWAVE_OPERATING_MODE_RX_AND_TX | GGWAVE_OPERATING_MODE_USE_DSS;
|
||||
instance = ggwave.init(parameters);
|
||||
}
|
||||
}
|
||||
@@ -122,7 +123,7 @@
|
||||
}
|
||||
|
||||
// generate audio waveform
|
||||
var waveform = ggwave.encode(instance, payload, ggwave.TxProtocolId.GGWAVE_TX_PROTOCOL_MT_FASTEST, 25)
|
||||
var waveform = ggwave.encode(instance, payload, ggwave.TxProtocolId.GGWAVE_PROTOCOL_MT_FASTEST, 25)
|
||||
|
||||
// play audio
|
||||
var buf = convertTypedArray(waveform, Float32Array);
|
||||
|
||||
@@ -48,29 +48,20 @@ void loop() {
|
||||
Serial.println("trying to create ggwave instance");
|
||||
|
||||
auto p = GGWave::getDefaultParameters();
|
||||
p.sampleRateInp = frequency;
|
||||
p.sampleRateOut = frequency;
|
||||
p.sampleRate = frequency;
|
||||
p.sampleFormatInp = GGWAVE_SAMPLE_FORMAT_I16;
|
||||
p.payloadLength = 16;
|
||||
p.sampleRateInp = frequency;
|
||||
p.sampleRateOut = frequency;
|
||||
p.sampleRate = frequency;
|
||||
p.samplesPerFrame = 128;
|
||||
p.payloadLength = 16;
|
||||
p.operatingMode = (ggwave_OperatingMode) (GGWAVE_OPERATING_MODE_RX | GGWAVE_OPERATING_MODE_TX | GGWAVE_OPERATING_MODE_USE_DSS | GGWAVE_OPERATING_MODE_TX_ONLY_TONES);
|
||||
p.sampleFormatInp = GGWAVE_SAMPLE_FORMAT_I16;
|
||||
p.sampleFormatOut = GGWAVE_SAMPLE_FORMAT_I16;
|
||||
p.operatingMode = (ggwave_OperatingMode) (GGWAVE_OPERATING_MODE_RX | GGWAVE_OPERATING_MODE_TX | GGWAVE_OPERATING_MODE_USE_DSS | GGWAVE_OPERATING_MODE_TX_ONLY_TONES);
|
||||
|
||||
{
|
||||
auto & protocols = GGWave::getTxProtocols();
|
||||
for (auto & p : protocols) {
|
||||
p.enabled = false;
|
||||
}
|
||||
protocols[GGWAVE_TX_PROTOCOL_MT_FASTEST].enabled = true;
|
||||
protocols[GGWAVE_TX_PROTOCOL_DT_FASTEST].enabled = true;
|
||||
}
|
||||
GGWave::Protocols::tx().only({GGWAVE_PROTOCOL_MT_FASTEST, GGWAVE_PROTOCOL_DT_FASTEST});
|
||||
GGWave::Protocols::rx().only({GGWAVE_PROTOCOL_MT_FASTEST, GGWAVE_PROTOCOL_DT_FASTEST});
|
||||
|
||||
GGWave ggwave(p);
|
||||
ggwave.setLogFile(nullptr);
|
||||
ggwave.setRxProtocols({
|
||||
ggwave.getTxProtocol(GGWAVE_TX_PROTOCOL_MT_FASTEST),
|
||||
ggwave.getTxProtocol(GGWAVE_TX_PROTOCOL_DT_FASTEST),
|
||||
});
|
||||
|
||||
Serial.println("Instance initialized");
|
||||
|
||||
@@ -103,14 +94,14 @@ void loop() {
|
||||
Serial.println(tEnd - tStart);
|
||||
}
|
||||
|
||||
nr = ggwave.takeRxData(result);
|
||||
nr = ggwave.rxTakeData(result);
|
||||
if (nr > 0) {
|
||||
Serial.println(tEnd - tStart);
|
||||
Serial.println(nr);
|
||||
Serial.println((char *)result.data());
|
||||
|
||||
if (strcmp((char *)result.data(), "test") == 0) {
|
||||
ggwave.init("hello", ggwave.getTxProtocol(GGWAVE_TX_PROTOCOL_MT_FASTEST));
|
||||
ggwave.init("hello", GGWave::TxProtocolId(GGWAVE_PROTOCOL_MT_FASTEST));
|
||||
ggwave.encode();
|
||||
|
||||
const auto & tones = ggwave.txTones();
|
||||
|
||||
1
examples/arduino-tx/.gitignore
vendored
1
examples/arduino-tx/.gitignore
vendored
@@ -1,5 +1,6 @@
|
||||
ggwave
|
||||
ggwave.cpp
|
||||
fft.h
|
||||
resampler.h
|
||||
resampler.cpp
|
||||
reed-solomon
|
||||
|
||||
@@ -1,9 +1,10 @@
|
||||
#
|
||||
# arduino-tx
|
||||
|
||||
configure_file(${CMAKE_SOURCE_DIR}/include/ggwave/ggwave.h ${CMAKE_CURRENT_SOURCE_DIR}/ggwave/ggwave.h COPYONLY)
|
||||
configure_file(${CMAKE_SOURCE_DIR}/src/ggwave.cpp ${CMAKE_CURRENT_SOURCE_DIR}/ggwave.cpp COPYONLY)
|
||||
configure_file(${CMAKE_SOURCE_DIR}/src/reed-solomon/gf.hpp ${CMAKE_CURRENT_SOURCE_DIR}/reed-solomon/gf.hpp COPYONLY)
|
||||
configure_file(${CMAKE_SOURCE_DIR}/src/reed-solomon/rs.hpp ${CMAKE_CURRENT_SOURCE_DIR}/reed-solomon/rs.hpp COPYONLY)
|
||||
configure_file(${CMAKE_SOURCE_DIR}/include/ggwave/ggwave.h ${CMAKE_CURRENT_SOURCE_DIR}/ggwave/ggwave.h COPYONLY)
|
||||
configure_file(${CMAKE_SOURCE_DIR}/src/ggwave.cpp ${CMAKE_CURRENT_SOURCE_DIR}/ggwave.cpp COPYONLY)
|
||||
configure_file(${CMAKE_SOURCE_DIR}/src/fft.h ${CMAKE_CURRENT_SOURCE_DIR}/fft.h COPYONLY)
|
||||
configure_file(${CMAKE_SOURCE_DIR}/src/reed-solomon/gf.hpp ${CMAKE_CURRENT_SOURCE_DIR}/reed-solomon/gf.hpp COPYONLY)
|
||||
configure_file(${CMAKE_SOURCE_DIR}/src/reed-solomon/rs.hpp ${CMAKE_CURRENT_SOURCE_DIR}/reed-solomon/rs.hpp COPYONLY)
|
||||
configure_file(${CMAKE_SOURCE_DIR}/src/reed-solomon/poly.hpp ${CMAKE_CURRENT_SOURCE_DIR}/reed-solomon/poly.hpp COPYONLY)
|
||||
configure_file(${CMAKE_SOURCE_DIR}/src/reed-solomon/LICENSE ${CMAKE_CURRENT_SOURCE_DIR}/reed-solomon/LICENSE COPYONLY)
|
||||
configure_file(${CMAKE_SOURCE_DIR}/src/reed-solomon/LICENSE ${CMAKE_CURRENT_SOURCE_DIR}/reed-solomon/LICENSE COPYONLY)
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
#include <ArduinoSTL.h>
|
||||
#include "Arduino_AVRSTL.h"
|
||||
|
||||
#include "ggwave/ggwave.h"
|
||||
|
||||
@@ -9,6 +9,7 @@ const int kPinButton1 = 4;
|
||||
|
||||
void setup() {
|
||||
Serial.begin(57600);
|
||||
display_freeram();
|
||||
|
||||
//pinMode(kPinLed0, OUTPUT);
|
||||
//pinMode(kPinSpeaker, OUTPUT);
|
||||
@@ -61,17 +62,42 @@ char txt[16];
|
||||
int pressed = 0;
|
||||
bool isDown = false;
|
||||
|
||||
void display_freeram() {
|
||||
Serial.print(F("- SRAM left: "));
|
||||
Serial.println(freeRam());
|
||||
}
|
||||
|
||||
int freeRam() {
|
||||
extern int __heap_start,*__brkval;
|
||||
int v;
|
||||
return (int)&v - (__brkval == 0 ? (int)&__heap_start : (int) __brkval);
|
||||
}
|
||||
|
||||
void loop() {
|
||||
Serial.println("hello");
|
||||
|
||||
auto p = GGWave::getDefaultParameters();
|
||||
p.sampleFormatInp = GGWAVE_SAMPLE_FORMAT_I16;
|
||||
p.payloadLength = 4;
|
||||
p.sampleRateInp = 6000;
|
||||
p.sampleRateOut = 6000;
|
||||
p.sampleRate = 6000;
|
||||
p.samplesPerFrame = 128;
|
||||
p.payloadLength = 4;
|
||||
p.operatingMode = (ggwave_OperatingMode) (GGWAVE_OPERATING_MODE_TX | GGWAVE_OPERATING_MODE_TX_ONLY_TONES);
|
||||
p.sampleFormatInp = GGWAVE_SAMPLE_FORMAT_I16;
|
||||
p.sampleFormatOut = GGWAVE_SAMPLE_FORMAT_U8;
|
||||
p.operatingMode = (ggwave_OperatingMode) (GGWAVE_OPERATING_MODE_TX | GGWAVE_OPERATING_MODE_TX_ONLY_TONES);
|
||||
|
||||
GGWave::getTxProtocols() = GGWave::TxProtocols({{ "[MT] Fastest", 24, 3, 1, 2, true, }});
|
||||
delay(1000);
|
||||
GGWave::Protocols::kDefault() = {};
|
||||
Serial.println("aaaaaaaaaaaa");
|
||||
GGWave::Protocols::tx() = { { "[MT] Fastest", 24, 3, 1, 2, true, } };
|
||||
|
||||
delay(1000);
|
||||
display_freeram();
|
||||
Serial.println("xxxxxxxxxxx");
|
||||
delay(1000);
|
||||
Serial.println("yyyyyyyyyyyy");
|
||||
GGWave ggwave(p);
|
||||
display_freeram();
|
||||
|
||||
while (true) {
|
||||
delay(1000);
|
||||
|
||||
@@ -40,17 +40,17 @@
|
||||
|
||||
<script type="text/javascript" src="ggwave.js"></script>
|
||||
<script type='text/javascript'>
|
||||
window.AudioContext = window.AudioContext || window.webkitAudioContext;
|
||||
window.AudioContext = window.AudioContext || window.webkitAudioContext;
|
||||
window.OfflineAudioContext = window.OfflineAudioContext || window.webkitOfflineAudioContext;
|
||||
|
||||
var context = null;
|
||||
var context = null;
|
||||
var recorder = null;
|
||||
|
||||
// the ggwave module instance
|
||||
var ggwave = null;
|
||||
var ggwave = null;
|
||||
var ggwave_FluentPet = null;
|
||||
var parameters = null;
|
||||
var instance = null;
|
||||
var parameters = null;
|
||||
var instance = null;
|
||||
|
||||
const kPayloadLength = 3;
|
||||
|
||||
@@ -65,10 +65,10 @@
|
||||
ggwave_FluentPet = obj;
|
||||
});
|
||||
|
||||
var txData = document.getElementById("txData");
|
||||
var rxData = document.getElementById("rxData");
|
||||
var txData = document.getElementById("txData");
|
||||
var rxData = document.getElementById("rxData");
|
||||
var captureStart = document.getElementById("captureStart");
|
||||
var captureStop = document.getElementById("captureStop");
|
||||
var captureStop = document.getElementById("captureStop");
|
||||
|
||||
// helper function
|
||||
function convertTypedArray(src, type) {
|
||||
@@ -113,9 +113,9 @@
|
||||
// generate audio waveform
|
||||
var waveform = null;
|
||||
if (document.getElementById("checkbox-fp").checked) {
|
||||
waveform = ggwave_FluentPet.encode(instance, payload, ggwave_FluentPet.TxProtocolId.GGWAVE_TX_PROTOCOL_DT_FAST, 25)
|
||||
waveform = ggwave_FluentPet.encode(instance, payload, ggwave_FluentPet.TxProtocolId.GGWAVE_PROTOCOL_DT_FAST, 25)
|
||||
} else {
|
||||
waveform = ggwave.encode(instance, payload, ggwave.TxProtocolId.GGWAVE_TX_PROTOCOL_DT_FAST, 25)
|
||||
waveform = ggwave.encode(instance, payload, ggwave.TxProtocolId.GGWAVE_PROTOCOL_DT_FAST, 25)
|
||||
}
|
||||
|
||||
// play audio
|
||||
|
||||
@@ -22,13 +22,13 @@ int main(int argc, char** argv) {
|
||||
printf(" -v - print generated tones on resend\n");
|
||||
printf("\n");
|
||||
|
||||
const auto argm = parseCmdArguments(argc, argv);
|
||||
const int captureId = argm.count("c") == 0 ? 0 : std::stoi(argm.at("c"));
|
||||
const int playbackId = argm.count("p") == 0 ? 0 : std::stoi(argm.at("p"));
|
||||
const int txProtocolId = argm.count("t") == 0 ? 1 : std::stoi(argm.at("t"));
|
||||
const auto argm = parseCmdArguments(argc, argv);
|
||||
const int captureId = argm.count("c") == 0 ? 0 : std::stoi(argm.at("c"));
|
||||
const int playbackId = argm.count("p") == 0 ? 0 : std::stoi(argm.at("p"));
|
||||
const int txProtocolId = argm.count("t") == 0 ? 1 : std::stoi(argm.at("t"));
|
||||
const int payloadLength = argm.count("l") == 0 ? -1 : std::stoi(argm.at("l"));
|
||||
const bool useDSS = argm.count("s") > 0;
|
||||
const bool printTones = argm.count("v") > 0;
|
||||
const bool useDSS = argm.count("s") > 0;
|
||||
const bool printTones = argm.count("v") > 0;
|
||||
|
||||
if (GGWave_init(playbackId, captureId, payloadLength, 0.0f, useDSS) == false) {
|
||||
fprintf(stderr, "Failed to initialize GGWave\n");
|
||||
@@ -38,7 +38,7 @@ int main(int argc, char** argv) {
|
||||
auto ggWave = GGWave_instance();
|
||||
|
||||
printf("Available Tx protocols:\n");
|
||||
const auto & protocols = GGWave::getTxProtocols();
|
||||
const auto & protocols = GGWave::Protocols::kDefault();
|
||||
for (int i = 0; i < (int) protocols.size(); ++i) {
|
||||
const auto & protocol = protocols[i];
|
||||
if (protocol.enabled == false) {
|
||||
@@ -82,7 +82,7 @@ int main(int argc, char** argv) {
|
||||
}
|
||||
{
|
||||
std::lock_guard<std::mutex> lock(mutex);
|
||||
ggWave->init(input.size(), input.data(), ggWave->getTxProtocol(txProtocolId), 10);
|
||||
ggWave->init(input.size(), input.data(), GGWave::TxProtocolId(txProtocolId), 10);
|
||||
}
|
||||
inputOld = input;
|
||||
}
|
||||
|
||||
@@ -34,41 +34,39 @@ std::shared_ptr<GGWave> g_ggWave = nullptr;
|
||||
extern "C" {
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int sendData(int textLength, const char * text, int protocolId, int volume) {
|
||||
g_ggWave->init(textLength, text, g_ggWave->getTxProtocol(protocolId), volume);
|
||||
g_ggWave->init(textLength, text, GGWave::TxProtocolId(protocolId), volume);
|
||||
return 0;
|
||||
}
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int getText(char * text) {
|
||||
std::copy(g_ggWave->getRxData().begin(), g_ggWave->getRxData().end(), text);
|
||||
std::copy(g_ggWave->rxData().begin(), g_ggWave->rxData().end(), text);
|
||||
return 0;
|
||||
}
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
float getSampleRate() { return g_ggWave->getSampleRateInp(); }
|
||||
float sampleRate() { return g_ggWave->sampleRateInp(); }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int getFramesToRecord() { return g_ggWave->getFramesToRecord(); }
|
||||
int framesToRecord() { return g_ggWave->rxFramesToRecord(); }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int getFramesLeftToRecord() { return g_ggWave->getFramesLeftToRecord(); }
|
||||
int framesLeftToRecord() { return g_ggWave->rxFramesLeftToRecord(); }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int getFramesToAnalyze() { return g_ggWave->getFramesToAnalyze(); }
|
||||
int framesToAnalyze() { return g_ggWave->rxFramesToAnalyze(); }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int getFramesLeftToAnalyze() { return g_ggWave->getFramesLeftToAnalyze(); }
|
||||
int framesLeftToAnalyze() { return g_ggWave->rxFramesLeftToAnalyze(); }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int hasDeviceOutput() { return g_devIdOut; }
|
||||
int hasDeviceOutput() { return g_devIdOut; }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int hasDeviceCapture() { return g_devIdInp; }
|
||||
int hasDeviceCapture() { return g_devIdInp; }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int doInit() {
|
||||
return GGWave_init(-1, -1);
|
||||
}
|
||||
int doInit() { return GGWave_init(-1, -1); }
|
||||
}
|
||||
|
||||
void GGWave_setDefaultCaptureDeviceName(std::string name) {
|
||||
@@ -244,16 +242,16 @@ bool GGWave_mainLoop() {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (g_ggWave->hasTxData() == false) {
|
||||
if (g_ggWave->txHasData() == false) {
|
||||
SDL_PauseAudioDevice(g_devIdOut, SDL_FALSE);
|
||||
|
||||
static auto tLastNoData = std::chrono::high_resolution_clock::now();
|
||||
auto tNow = std::chrono::high_resolution_clock::now();
|
||||
|
||||
if ((int) SDL_GetQueuedAudioSize(g_devIdOut) < g_ggWave->getSamplesPerFrame()*g_ggWave->getSampleSizeBytesOut()) {
|
||||
if ((int) SDL_GetQueuedAudioSize(g_devIdOut) < g_ggWave->samplesPerFrame()*g_ggWave->sampleSizeOut()) {
|
||||
SDL_PauseAudioDevice(g_devIdInp, SDL_FALSE);
|
||||
const int nHave = (int) SDL_GetQueuedAudioSize(g_devIdInp);
|
||||
const int nNeed = g_ggWave->getSamplesPerFrame()*g_ggWave->getSampleSizeBytesInp();
|
||||
const int nNeed = g_ggWave->samplesPerFrame()*g_ggWave->sampleSizeInp();
|
||||
if (::getTime_ms(tLastNoData, tNow) > 500.0f && nHave >= nNeed) {
|
||||
static std::vector<uint8_t> dataInp(nNeed);
|
||||
SDL_DequeueAudio(g_devIdInp, dataInp.data(), nNeed);
|
||||
|
||||
@@ -4,7 +4,7 @@ import pyaudio
|
||||
p = pyaudio.PyAudio()
|
||||
|
||||
# generate audio waveform for string "hello python"
|
||||
waveform = ggwave.encode("hello python", txProtocolId = 1, volume = 20)
|
||||
waveform = ggwave.encode("hello python", protocolId = 1, volume = 20)
|
||||
|
||||
print("Transmitting text 'hello python' ...")
|
||||
stream = p.open(format=pyaudio.paFloat32, channels=1, rate=48000, output=True, frames_per_buffer=4096)
|
||||
|
||||
@@ -12,13 +12,14 @@
|
||||
int main(int argc, char** argv) {
|
||||
fprintf(stderr, "Usage: %s [-vN] [-sN] [-pN] [-lN]\n", argv[0]);
|
||||
fprintf(stderr, " -vN - output volume, N in (0, 100], (default: 50)\n");
|
||||
fprintf(stderr, " -sN - output sample rate, N in [%d, %d], (default: %d)\n", (int) GGWave::kSampleRateMin, (int) GGWave::kSampleRateMax, (int) GGWave::kDefaultSampleRate);
|
||||
fprintf(stderr, " -SN - output sample rate, N in [%d, %d], (default: %d)\n", (int) GGWave::kSampleRateMin, (int) GGWave::kSampleRateMax, (int) GGWave::kDefaultSampleRate);
|
||||
fprintf(stderr, " -pN - select the transmission protocol id (default: 1)\n");
|
||||
fprintf(stderr, " -lN - fixed payload length of size N, N in [1, %d]\n", GGWave::kMaxLengthFixed);
|
||||
fprintf(stderr, " -s - use Direct Sequence Spread (DSS)\n");
|
||||
fprintf(stderr, "\n");
|
||||
fprintf(stderr, " Available protocols:\n");
|
||||
|
||||
const auto & protocols = GGWave::getTxProtocols();
|
||||
const auto & protocols = GGWave::Protocols::kDefault();
|
||||
for (int i = 0; i < (int) protocols.size(); ++i) {
|
||||
const auto & protocol = protocols[i];
|
||||
fprintf(stderr, " %d - %s\n", i, protocol.name);
|
||||
@@ -29,16 +30,17 @@ int main(int argc, char** argv) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
auto argm = parseCmdArguments(argc, argv);
|
||||
const auto argm = parseCmdArguments(argc, argv);
|
||||
|
||||
if (argm.find("h") != argm.end()) {
|
||||
if (argm.count("h") > 0) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
int volume = argm["v"].empty() ? 50 : std::stoi(argm["v"]);
|
||||
float sampleRateOut = argm["s"].empty() ? GGWave::kDefaultSampleRate : std::stof(argm["s"]);
|
||||
int protocolId = argm["p"].empty() ? 1 : std::stoi(argm["p"]);
|
||||
int payloadLength = argm["l"].empty() ? -1 : std::stoi(argm["l"]);
|
||||
const int volume = argm.count("v") == 0 ? 50 : std::stoi(argm.at("v"));
|
||||
const float sampleRateOut = argm.count("S") == 0 ? GGWave::kDefaultSampleRate : std::stof(argm.at("S"));
|
||||
const int protocolId = argm.count("p") == 0 ? 1 : std::stoi(argm.at("p"));
|
||||
const int payloadLength = argm.count("l") == 0 ? -1 : std::stoi(argm.at("l"));
|
||||
const bool useDSS = argm.count("s") > 0;
|
||||
|
||||
if (volume <= 0 || volume > 100) {
|
||||
fprintf(stderr, "Invalid volume\n");
|
||||
@@ -50,11 +52,16 @@ int main(int argc, char** argv) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (protocolId < 0 || protocolId >= (int) GGWave::getTxProtocols().size()) {
|
||||
if (protocolId < 0 || protocolId >= (int) protocols.size()) {
|
||||
fprintf(stderr, "Invalid transmission protocol id\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (protocols[protocolId].enabled == false) {
|
||||
fprintf(stderr, "Protocol %d is not enabled\n", protocolId);
|
||||
return -1;
|
||||
}
|
||||
|
||||
fprintf(stderr, "Enter a text message:\n");
|
||||
|
||||
std::string message;
|
||||
@@ -72,6 +79,9 @@ int main(int argc, char** argv) {
|
||||
|
||||
fprintf(stderr, "Generating waveform for message '%s' ...\n", message.c_str());
|
||||
|
||||
ggwave_OperatingMode mode = GGWAVE_OPERATING_MODE_RX_AND_TX;
|
||||
if (useDSS) mode = ggwave_OperatingMode(mode | GGWAVE_OPERATING_MODE_USE_DSS);
|
||||
|
||||
GGWave ggWave({
|
||||
payloadLength,
|
||||
GGWave::kDefaultSampleRate,
|
||||
@@ -81,9 +91,9 @@ int main(int argc, char** argv) {
|
||||
GGWave::kDefaultSoundMarkerThreshold,
|
||||
GGWAVE_SAMPLE_FORMAT_F32,
|
||||
GGWAVE_SAMPLE_FORMAT_I16,
|
||||
GGWAVE_OPERATING_MODE_RX_AND_TX,
|
||||
mode,
|
||||
});
|
||||
ggWave.init(message.size(), message.data(), ggWave.getTxProtocol(protocolId), volume);
|
||||
ggWave.init(message.size(), message.data(), GGWave::TxProtocolId(protocolId), volume);
|
||||
|
||||
const auto nBytes = ggWave.encode();
|
||||
if (nBytes == 0) {
|
||||
|
||||
@@ -48,11 +48,13 @@ int main(int argc, char** argv) {
|
||||
printf(" -p - print tones, no playback\n");
|
||||
printf(" -A - print Arduino code\n");
|
||||
printf(" -b - use 'beep' command\n");
|
||||
printf(" -s - use Direct Sequence Spread (DSS)\n");
|
||||
printf(" -tN - transmission protocol\n");
|
||||
printf(" -lN - fixed payload length of size N, N in [1, %d]\n", GGWave::kMaxLengthFixed);
|
||||
printf("\n");
|
||||
|
||||
const GGWave::TxProtocols protocols = {
|
||||
auto & protocols = GGWave::Protocols::tx();
|
||||
protocols = {
|
||||
{ "[R2T2] Normal", 64, 9, 1, 2, true, },
|
||||
{ "[R2T2] Fast", 64, 6, 1, 2, true, },
|
||||
{ "[R2T2] Fastest", 64, 3, 1, 2, true, },
|
||||
@@ -61,13 +63,17 @@ int main(int argc, char** argv) {
|
||||
{ "[R2T2] Low Fastest", 16, 3, 1, 2, true, },
|
||||
};
|
||||
|
||||
const auto argm = parseCmdArguments(argc, argv);
|
||||
const bool printTones = argm.count("p") > 0;
|
||||
const auto argm = parseCmdArguments(argc, argv);
|
||||
const bool printTones = argm.count("p") > 0;
|
||||
const bool printArduino = argm.count("A") > 0;
|
||||
const bool useBeep = argm.count("b") > 0;
|
||||
const int txProtocolId = argm.count("t") == 0 ? GGWAVE_TX_PROTOCOL_CUSTOM_0 : std::stoi(argm.at("t"));
|
||||
const bool useBeep = argm.count("b") > 0;
|
||||
const bool useDSS = argm.count("s") > 0;
|
||||
const int txProtocolId = argm.count("t") == 0 ? 0 : std::stoi(argm.at("t"));
|
||||
const int payloadLength = argm.count("l") == 0 ? 16 : std::stoi(argm.at("l"));
|
||||
|
||||
ggwave_OperatingMode mode = ggwave_OperatingMode(GGWAVE_OPERATING_MODE_TX | GGWAVE_OPERATING_MODE_TX_ONLY_TONES);
|
||||
if (useDSS) mode = ggwave_OperatingMode(mode | GGWAVE_OPERATING_MODE_USE_DSS);
|
||||
|
||||
GGWave ggWave({
|
||||
payloadLength,
|
||||
GGWave::kDefaultSampleRate,
|
||||
@@ -77,7 +83,7 @@ int main(int argc, char** argv) {
|
||||
GGWave::kDefaultSoundMarkerThreshold,
|
||||
GGWAVE_SAMPLE_FORMAT_F32,
|
||||
GGWAVE_SAMPLE_FORMAT_F32,
|
||||
(ggwave_OperatingMode) (GGWAVE_OPERATING_MODE_TX | GGWAVE_OPERATING_MODE_TX_ONLY_TONES),
|
||||
mode,
|
||||
});
|
||||
|
||||
printf("Available Tx protocols:\n");
|
||||
@@ -123,7 +129,7 @@ int main(int argc, char** argv) {
|
||||
return -3;
|
||||
}
|
||||
|
||||
ggWave.init(message.size(), message.data(), protocols.at(GGWave::TxProtocolId(txProtocolId)), 10);
|
||||
ggWave.init(message.size(), message.data(), GGWave::TxProtocolId(txProtocolId), 10);
|
||||
ggWave.encode();
|
||||
|
||||
int nFrames = 0;
|
||||
|
||||
@@ -44,41 +44,39 @@ void mainUpdate(void *) {
|
||||
extern "C" {
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int sendData(int textLength, const char * text, int protocolId, int volume) {
|
||||
g_ggWave->init(textLength, text, g_ggWave->getTxProtocol(protocolId), volume);
|
||||
g_ggWave->init(textLength, text, GGWave::TxProtocolId(protocolId), volume);
|
||||
return 0;
|
||||
}
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int getText(char * text) {
|
||||
std::copy(g_ggWave->getRxData().begin(), g_ggWave->getRxData().end(), text);
|
||||
std::copy(g_ggWave->rxData().begin(), g_ggWave->rxData().end(), text);
|
||||
return 0;
|
||||
}
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
float getSampleRate() { return g_ggWave->getSampleRateInp(); }
|
||||
float sampleRate() { return g_ggWave->sampleRateInp(); }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int getFramesToRecord() { return g_ggWave->getFramesToRecord(); }
|
||||
int framesToRecord() { return g_ggWave->rxFramesToRecord(); }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int getFramesLeftToRecord() { return g_ggWave->getFramesLeftToRecord(); }
|
||||
int framesLeftToRecord() { return g_ggWave->rxFramesLeftToRecord(); }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int getFramesToAnalyze() { return g_ggWave->getFramesToAnalyze(); }
|
||||
int framesToAnalyze() { return g_ggWave->rxFramesToAnalyze(); }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int getFramesLeftToAnalyze() { return g_ggWave->getFramesLeftToAnalyze(); }
|
||||
int framesLeftToAnalyze() { return g_ggWave->rxFramesLeftToAnalyze(); }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int hasDeviceOutput() { return g_devIdOut; }
|
||||
int hasDeviceOutput() { return g_devIdOut; }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int hasDeviceCapture() { return g_devIdInp; }
|
||||
int hasDeviceCapture() { return g_devIdInp; }
|
||||
|
||||
EMSCRIPTEN_KEEPALIVE
|
||||
int doInit() {
|
||||
return g_doInit();
|
||||
}
|
||||
int doInit() { return g_doInit(); }
|
||||
}
|
||||
|
||||
void GGWave_setDefaultCaptureDeviceName(std::string name) {
|
||||
@@ -89,7 +87,8 @@ bool GGWave_init(
|
||||
const int playbackId,
|
||||
const int captureId,
|
||||
const int payloadLength,
|
||||
const float sampleRateOffset) {
|
||||
const float sampleRateOffset,
|
||||
const bool useDSS) {
|
||||
|
||||
if (g_devIdInp && g_devIdOut) {
|
||||
return false;
|
||||
@@ -225,6 +224,9 @@ bool GGWave_init(
|
||||
if (reinit) {
|
||||
if (g_ggWave) delete g_ggWave;
|
||||
|
||||
ggwave_OperatingMode mode = GGWAVE_OPERATING_MODE_RX;
|
||||
if (useDSS) mode = ggwave_OperatingMode(mode | GGWAVE_OPERATING_MODE_USE_DSS);
|
||||
|
||||
g_ggWave = new GGWave({
|
||||
payloadLength,
|
||||
(float) g_obtainedSpecInp.freq,
|
||||
@@ -234,7 +236,7 @@ bool GGWave_init(
|
||||
GGWave::kDefaultSoundMarkerThreshold,
|
||||
sampleFormatInp,
|
||||
sampleFormatOut,
|
||||
GGWAVE_OPERATING_MODE_RX,
|
||||
mode,
|
||||
});
|
||||
}
|
||||
|
||||
@@ -248,16 +250,16 @@ bool GGWave_mainLoop() {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (g_ggWave->hasTxData() == false) {
|
||||
if (g_ggWave->txHasData() == false) {
|
||||
SDL_PauseAudioDevice(g_devIdOut, SDL_FALSE);
|
||||
|
||||
static auto tLastNoData = std::chrono::high_resolution_clock::now();
|
||||
auto tNow = std::chrono::high_resolution_clock::now();
|
||||
|
||||
if ((int) SDL_GetQueuedAudioSize(g_devIdOut) < g_ggWave->getSamplesPerFrame()*g_ggWave->getSampleSizeBytesOut()) {
|
||||
if ((int) SDL_GetQueuedAudioSize(g_devIdOut) < g_ggWave->samplesPerFrame()*g_ggWave->sampleSizeOut()) {
|
||||
SDL_PauseAudioDevice(g_devIdInp, SDL_FALSE);
|
||||
const int nHave = (int) SDL_GetQueuedAudioSize(g_devIdInp);
|
||||
const int nNeed = g_ggWave->getSamplesPerFrame()*g_ggWave->getSampleSizeBytesInp();
|
||||
const int nNeed = g_ggWave->samplesPerFrame()*g_ggWave->sampleSizeInp();
|
||||
if (::getTime_ms(tLastNoData, tNow) > 500.0f && nHave >= nNeed) {
|
||||
static std::vector<uint8_t> dataInp(nNeed);
|
||||
SDL_DequeueAudio(g_devIdInp, dataInp.data(), nNeed);
|
||||
@@ -318,10 +320,12 @@ int main(int argc, char** argv) {
|
||||
printf("Usage: %s [-cN] [-lN]\n", argv[0]);
|
||||
printf(" -cN - select capture device N\n");
|
||||
printf(" -lN - fixed payload length of size N, N in [1, %d]\n", GGWave::kMaxLengthFixed);
|
||||
printf(" -s - use Direct Sequence Spread (DSS)\n");
|
||||
printf("\n");
|
||||
#endif
|
||||
|
||||
const GGWave::TxProtocols protocols = {
|
||||
auto & protocols = GGWave::Protocols::rx();
|
||||
protocols = {
|
||||
{ "[R2T2] Normal", 64, 9, 1, 2, true, },
|
||||
{ "[R2T2] Fast", 64, 6, 1, 2, true, },
|
||||
{ "[R2T2] Fastest", 64, 3, 1, 2, true, },
|
||||
@@ -330,20 +334,19 @@ int main(int argc, char** argv) {
|
||||
{ "[R2T2] Low Fastest", 16, 3, 1, 2, true, },
|
||||
};
|
||||
|
||||
const auto argm = parseCmdArguments(argc, argv);
|
||||
const int captureId = argm.count("c") == 0 ? 0 : std::stoi(argm.at("c"));
|
||||
const auto argm = parseCmdArguments(argc, argv);
|
||||
const int captureId = argm.count("c") == 0 ? 0 : std::stoi(argm.at("c"));
|
||||
const int payloadLength = argm.count("l") == 0 ? 16 : std::stoi(argm.at("l"));
|
||||
const bool useDSS = argm.count("s") > 0;
|
||||
|
||||
bool isInitialized = false;
|
||||
|
||||
g_doInit = [&]() {
|
||||
if (GGWave_init(0, captureId, payloadLength, 0) == false) {
|
||||
if (GGWave_init(0, captureId, payloadLength, 0, useDSS) == false) {
|
||||
fprintf(stderr, "Failed to initialize GGWave\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
g_ggWave->setRxProtocols(protocols);
|
||||
|
||||
isInitialized = true;
|
||||
printf("Listening for payload with length = %d bytes ..\n", payloadLength);
|
||||
|
||||
|
||||
@@ -136,8 +136,8 @@ struct Message {
|
||||
};
|
||||
|
||||
struct GGWaveStats {
|
||||
bool isReceiving;
|
||||
bool isAnalyzing;
|
||||
bool receiving;
|
||||
bool analyzing;
|
||||
int framesToRecord;
|
||||
int framesLeftToRecord;
|
||||
int framesToAnalyze;
|
||||
@@ -146,8 +146,8 @@ struct GGWaveStats {
|
||||
float sampleRateInp;
|
||||
float sampleRateOut;
|
||||
float sampleRate;
|
||||
int sampleSizeBytesInp;
|
||||
int sampleSizeBytesOut;
|
||||
int sampleSizeInp;
|
||||
int sampleSizeOut;
|
||||
};
|
||||
|
||||
struct State {
|
||||
@@ -201,9 +201,11 @@ struct State {
|
||||
}
|
||||
|
||||
Message message;
|
||||
GGWave::SpectrumData rxSpectrum;
|
||||
GGWave::AmplitudeData rxAmplitude;
|
||||
GGWave::AmplitudeDataI16 txAmplitude;
|
||||
|
||||
GGWave::Spectrum rxSpectrum;
|
||||
GGWave::Amplitude rxAmplitude;
|
||||
GGWave::AmplitudeI16 txAmplitude;
|
||||
|
||||
GGWaveStats stats;
|
||||
GGWave::TxProtocols txProtocols;
|
||||
};
|
||||
@@ -302,7 +304,7 @@ GGSock::FileServer g_fileServer;
|
||||
|
||||
// file received data
|
||||
struct FileInfoExtended {
|
||||
bool isReceiving = false;
|
||||
bool receiving = false;
|
||||
bool readyToShare = false;
|
||||
bool requestToShare = false;
|
||||
int nReceivedChunks = 0;
|
||||
@@ -614,16 +616,16 @@ void updateCore() {
|
||||
|
||||
ggWave->init(
|
||||
n, inputCurrent.message.data.data(),
|
||||
ggWave->getTxProtocol(inputCurrent.message.protocolId),
|
||||
GGWave::TxProtocolId(inputCurrent.message.protocolId),
|
||||
100*inputCurrent.message.volume);
|
||||
}
|
||||
|
||||
if (inputCurrent.flags.needReinit) {
|
||||
static auto sampleRateInpOld = ggWave->getSampleRateInp();
|
||||
static auto sampleRateOutOld = ggWave->getSampleRateOut();
|
||||
GGWave::SampleFormat sampleFormatInpOld = ggWave->getSampleFormatInp();
|
||||
GGWave::SampleFormat sampleFormatOutOld = ggWave->getSampleFormatOut();
|
||||
auto rxProtocolsOld = ggWave->getRxProtocols();
|
||||
static auto sampleRateInpOld = ggWave->sampleRateInp();
|
||||
static auto sampleRateOutOld = ggWave->sampleRateOut();
|
||||
GGWave::SampleFormat sampleFormatInpOld = ggWave->sampleFormatInp();
|
||||
GGWave::SampleFormat sampleFormatOutOld = ggWave->sampleFormatOut();
|
||||
auto rxProtocolsOld = ggWave->rxProtocols();
|
||||
|
||||
GGWave::OperatingMode mode = GGWAVE_OPERATING_MODE_RX_AND_TX;
|
||||
if (inputCurrent.directSequenceSpread) mode = GGWave::OperatingMode(mode | GGWAVE_OPERATING_MODE_USE_DSS);
|
||||
@@ -643,7 +645,7 @@ void updateCore() {
|
||||
GGWave_reset(¶meters);
|
||||
ggWave = GGWave_instance();
|
||||
|
||||
ggWave->setRxProtocols(rxProtocolsOld);
|
||||
ggWave->rxProtocols() = rxProtocolsOld;
|
||||
}
|
||||
|
||||
if (inputCurrent.flags.changeNeedSpectrum) {
|
||||
@@ -651,11 +653,11 @@ void updateCore() {
|
||||
}
|
||||
|
||||
if (inputCurrent.flags.stopReceiving) {
|
||||
ggWave->stopReceiving();
|
||||
ggWave->rxStopReceiving();
|
||||
}
|
||||
|
||||
if (inputCurrent.flags.changeRxProtocols) {
|
||||
ggWave->setRxProtocols(inputCurrent.rxProtocols);
|
||||
ggWave->rxProtocols() = inputCurrent.rxProtocols;
|
||||
}
|
||||
|
||||
inputCurrent.flags.clear();
|
||||
@@ -664,7 +666,7 @@ void updateCore() {
|
||||
|
||||
GGWave_mainLoop();
|
||||
|
||||
rxDataLengthLast = ggWave->takeRxData(rxDataLast);
|
||||
rxDataLengthLast = ggWave->rxTakeData(rxDataLast);
|
||||
if (rxDataLengthLast == -1) {
|
||||
g_buffer.stateCore.update = true;
|
||||
g_buffer.stateCore.flags.newMessage = true;
|
||||
@@ -672,7 +674,7 @@ void updateCore() {
|
||||
true,
|
||||
std::chrono::system_clock::now(),
|
||||
"",
|
||||
ggWave->getRxProtocolId(),
|
||||
ggWave->rxProtocolId(),
|
||||
ggWave->isDSSEnabled(),
|
||||
0,
|
||||
Message::Error,
|
||||
@@ -687,7 +689,7 @@ void updateCore() {
|
||||
true,
|
||||
std::chrono::system_clock::now(),
|
||||
std::move(message),
|
||||
ggWave->getRxProtocolId(),
|
||||
ggWave->rxProtocolId(),
|
||||
ggWave->isDSSEnabled(),
|
||||
0,
|
||||
type,
|
||||
@@ -697,11 +699,11 @@ void updateCore() {
|
||||
}
|
||||
|
||||
if (needSpectrum) {
|
||||
if (ggWave->takeRxAmplitude(g_buffer.stateCore.rxAmplitude)) {
|
||||
if (ggWave->rxTakeAmplitude(g_buffer.stateCore.rxAmplitude)) {
|
||||
static const int NMax = GGWave::kMaxSamplesPerFrame;
|
||||
static float tmp[2*NMax];
|
||||
|
||||
int N = ggWave->getSamplesPerFrame();
|
||||
int N = ggWave->samplesPerFrame();
|
||||
ggWave->computeFFTR(g_buffer.stateCore.rxAmplitude.data(), tmp, N);
|
||||
|
||||
g_buffer.stateCore.rxSpectrum.resize(N);
|
||||
@@ -717,7 +719,7 @@ void updateCore() {
|
||||
}
|
||||
}
|
||||
|
||||
if (ggWave->takeTxAmplitudeI16(g_buffer.stateCore.txAmplitude)) {
|
||||
if (ggWave->txTakeAmplitudeI16(g_buffer.stateCore.txAmplitude)) {
|
||||
g_buffer.stateCore.update = true;
|
||||
g_buffer.stateCore.flags.newTxAmplitude = true;
|
||||
}
|
||||
@@ -725,24 +727,24 @@ void updateCore() {
|
||||
if (true) {
|
||||
g_buffer.stateCore.update = true;
|
||||
g_buffer.stateCore.flags.newStats = true;
|
||||
g_buffer.stateCore.stats.isReceiving = ggWave->isReceiving();
|
||||
g_buffer.stateCore.stats.isAnalyzing = ggWave->isAnalyzing();
|
||||
g_buffer.stateCore.stats.framesToRecord = ggWave->getFramesToRecord();
|
||||
g_buffer.stateCore.stats.framesLeftToRecord = ggWave->getFramesLeftToRecord();
|
||||
g_buffer.stateCore.stats.framesToAnalyze = ggWave->getFramesToAnalyze();
|
||||
g_buffer.stateCore.stats.framesLeftToAnalyze = ggWave->getFramesLeftToAnalyze();
|
||||
g_buffer.stateCore.stats.samplesPerFrame = ggWave->getSamplesPerFrame();
|
||||
g_buffer.stateCore.stats.sampleRateInp = ggWave->getSampleRateInp();
|
||||
g_buffer.stateCore.stats.sampleRateOut = ggWave->getSampleRateOut();
|
||||
g_buffer.stateCore.stats.sampleRate = GGWave::kDefaultSampleRate;
|
||||
g_buffer.stateCore.stats.sampleSizeBytesInp = ggWave->getSampleSizeBytesInp();
|
||||
g_buffer.stateCore.stats.sampleSizeBytesOut = ggWave->getSampleSizeBytesOut();
|
||||
g_buffer.stateCore.stats.receiving = ggWave->rxReceiving();
|
||||
g_buffer.stateCore.stats.analyzing = ggWave->rxAnalyzing();
|
||||
g_buffer.stateCore.stats.framesToRecord = ggWave->rxFramesToRecord();
|
||||
g_buffer.stateCore.stats.framesLeftToRecord = ggWave->rxFramesLeftToRecord();
|
||||
g_buffer.stateCore.stats.framesToAnalyze = ggWave->rxFramesToAnalyze();
|
||||
g_buffer.stateCore.stats.framesLeftToAnalyze = ggWave->rxFramesLeftToAnalyze();
|
||||
g_buffer.stateCore.stats.samplesPerFrame = ggWave->samplesPerFrame();
|
||||
g_buffer.stateCore.stats.sampleRateInp = ggWave->sampleRateInp();
|
||||
g_buffer.stateCore.stats.sampleRateOut = ggWave->sampleRateOut();
|
||||
g_buffer.stateCore.stats.sampleRate = GGWave::kDefaultSampleRate;
|
||||
g_buffer.stateCore.stats.sampleSizeInp = ggWave->sampleSizeInp();
|
||||
g_buffer.stateCore.stats.sampleSizeOut = ggWave->sampleSizeOut();
|
||||
}
|
||||
|
||||
if (isFirstCall) {
|
||||
g_buffer.stateCore.update = true;
|
||||
g_buffer.stateCore.flags.newTxProtocols = true;
|
||||
g_buffer.stateCore.txProtocols = ggWave->getTxProtocols();
|
||||
g_buffer.stateCore.txProtocols = GGWave::Protocols::tx();
|
||||
|
||||
isFirstCall = false;
|
||||
}
|
||||
@@ -773,7 +775,7 @@ void renderMain() {
|
||||
const auto & uri = fileInfo.second.uri;
|
||||
auto & fileInfoExtended = g_receivedFileInfosExtended[uri];
|
||||
|
||||
if (fileInfoExtended.isReceiving == false) {
|
||||
if (fileInfoExtended.receiving == false) {
|
||||
continue;
|
||||
}
|
||||
|
||||
@@ -835,7 +837,7 @@ void renderMain() {
|
||||
};
|
||||
|
||||
struct Settings {
|
||||
int protocolId = GGWAVE_TX_PROTOCOL_AUDIBLE_FAST;
|
||||
int protocolId = GGWAVE_PROTOCOL_AUDIBLE_FAST;
|
||||
bool isSampleRateOffset = false;
|
||||
float sampleRateOffset = -512.0f;
|
||||
bool isFixedLength = false;
|
||||
@@ -882,8 +884,8 @@ void renderMain() {
|
||||
static double tLengthTx = 0.0f;
|
||||
|
||||
static GGWaveStats statsCurrent;
|
||||
static GGWave::SpectrumData spectrumCurrent;
|
||||
static GGWave::AmplitudeDataI16 txAmplitudeDataCurrent;
|
||||
static GGWave::Spectrum spectrumCurrent;
|
||||
static GGWave::AmplitudeI16 txAmplitudeCurrent;
|
||||
static std::vector<Message> messageHistory;
|
||||
static std::string inputLast = "";
|
||||
|
||||
@@ -912,12 +914,12 @@ void renderMain() {
|
||||
hasAudioCaptureData = !spectrumCurrent.empty();
|
||||
}
|
||||
if (stateCurrent.flags.newTxAmplitude) {
|
||||
txAmplitudeDataCurrent = std::move(stateCurrent.txAmplitude);
|
||||
txAmplitudeCurrent = std::move(stateCurrent.txAmplitude);
|
||||
|
||||
tStartTx = ImGui::GetTime() + (16.0f*1024.0f)/statsCurrent.sampleRateOut;
|
||||
tLengthTx = txAmplitudeDataCurrent.size()/statsCurrent.sampleRateOut;
|
||||
tLengthTx = txAmplitudeCurrent.size()/statsCurrent.sampleRateOut;
|
||||
{
|
||||
auto & ampl = txAmplitudeDataCurrent;
|
||||
auto & ampl = txAmplitudeCurrent;
|
||||
int nBins = 512;
|
||||
int nspb = (int) ampl.size()/nBins;
|
||||
for (int i = 0; i < nBins; ++i) {
|
||||
@@ -1043,8 +1045,8 @@ void renderMain() {
|
||||
ImGui::Separator();
|
||||
|
||||
ImGui::Text("%s", "");
|
||||
ImGui::Text("Sample rate (capture): %g, %d B/sample", statsCurrent.sampleRateInp, statsCurrent.sampleSizeBytesInp);
|
||||
ImGui::Text("Sample rate (playback): %g, %d B/sample", statsCurrent.sampleRateOut, statsCurrent.sampleSizeBytesOut);
|
||||
ImGui::Text("Sample rate (capture): %g, %d B/sample", statsCurrent.sampleRateInp, statsCurrent.sampleSizeInp);
|
||||
ImGui::Text("Sample rate (playback): %g, %d B/sample", statsCurrent.sampleRateOut, statsCurrent.sampleSizeOut);
|
||||
|
||||
const float kLabelWidth = ImGui::CalcTextSize("Inp. SR Offset: ").x;
|
||||
|
||||
@@ -1501,8 +1503,8 @@ void renderMain() {
|
||||
}
|
||||
ImGui::EndChild();
|
||||
|
||||
if (statsCurrent.isReceiving) {
|
||||
if (statsCurrent.isAnalyzing) {
|
||||
if (statsCurrent.receiving) {
|
||||
if (statsCurrent.analyzing) {
|
||||
ImGui::TextColored({ 0.0f, 1.0f, 0.0f, 1.0f }, "Analyzing ...");
|
||||
ImGui::SameLine();
|
||||
ImGui::ProgressBar(1.0f - float(statsCurrent.framesLeftToAnalyze)/statsCurrent.framesToAnalyze,
|
||||
@@ -1525,7 +1527,7 @@ void renderMain() {
|
||||
amax = 0.0f;
|
||||
frac = (ImGui::GetTime() - tStartTx)/tLengthTx;
|
||||
|
||||
if (txAmplitudeDataCurrent.size() && frac <= 1.0f) {
|
||||
if (txAmplitudeCurrent.size() && frac <= 1.0f) {
|
||||
struct Funcs {
|
||||
static float Sample(void * data, int i) {
|
||||
auto res = std::fabs(((int16_t *)(data))[i]) ;
|
||||
@@ -1534,7 +1536,7 @@ void renderMain() {
|
||||
}
|
||||
|
||||
static float SampleFrac(void * data, int i) {
|
||||
if (i > frac*txAmplitudeDataCurrent.size()) {
|
||||
if (i > frac*txAmplitudeCurrent.size()) {
|
||||
return 0.0f;
|
||||
}
|
||||
return std::fabs(((int16_t *)(data))[i]);
|
||||
@@ -1550,8 +1552,8 @@ void renderMain() {
|
||||
ImGui::PushStyleColor(ImGuiCol_PlotHistogram, ImGui::GetStyleColorVec4(ImGuiCol_TextDisabled));
|
||||
ImGui::PlotHistogram("##plotSpectrumCurrent",
|
||||
Funcs::Sample,
|
||||
txAmplitudeDataCurrent.data(),
|
||||
(int) txAmplitudeDataCurrent.size(), 0,
|
||||
txAmplitudeCurrent.data(),
|
||||
(int) txAmplitudeCurrent.size(), 0,
|
||||
(std::string("")).c_str(),
|
||||
0.0f, FLT_MAX, wSize);
|
||||
ImGui::PopStyleColor(2);
|
||||
@@ -1562,8 +1564,8 @@ void renderMain() {
|
||||
ImGui::PushStyleColor(ImGuiCol_PlotHistogram, { 0.0f, 1.0f, 0.0f, 1.0f });
|
||||
ImGui::PlotHistogram("##plotSpectrumCurrent",
|
||||
Funcs::SampleFrac,
|
||||
txAmplitudeDataCurrent.data(),
|
||||
(int) txAmplitudeDataCurrent.size(), 0,
|
||||
txAmplitudeCurrent.data(),
|
||||
(int) txAmplitudeCurrent.size(), 0,
|
||||
(std::string("")).c_str(),
|
||||
0.0f, amax, wSize);
|
||||
ImGui::PopStyleColor(2);
|
||||
@@ -1835,14 +1837,14 @@ void renderMain() {
|
||||
if (fileInfoExtended.readyToShare) {
|
||||
ImGui::TextColored({ 0.0f, 1.0f, 0.0f, 1.0f }, "Ready to share!");
|
||||
}
|
||||
} else if (g_fileClient.isConnected() && (fileInfoExtended.isReceiving || fileInfoExtended.nReceivedChunks > 0)) {
|
||||
if (fileInfoExtended.isReceiving) {
|
||||
} else if (g_fileClient.isConnected() && (fileInfoExtended.receiving || fileInfoExtended.nReceivedChunks > 0)) {
|
||||
if (fileInfoExtended.receiving) {
|
||||
if (ImGui::Button(ICON_FA_PAUSE " Pause")) {
|
||||
fileInfoExtended.isReceiving = false;
|
||||
fileInfoExtended.receiving = false;
|
||||
}
|
||||
} else {
|
||||
if (ImGui::Button(ICON_FA_PLAY " Resume")) {
|
||||
fileInfoExtended.isReceiving = true;
|
||||
fileInfoExtended.receiving = true;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1850,7 +1852,7 @@ void renderMain() {
|
||||
ImGui::ProgressBar(float(fileInfoExtended.nReceivedChunks)/fileInfo.second.nChunks);
|
||||
} else if (g_fileClient.isConnected()) {
|
||||
if (ImGui::Button(ICON_FA_DOWNLOAD " Receive")) {
|
||||
fileInfoExtended.isReceiving = true;
|
||||
fileInfoExtended.receiving = true;
|
||||
fileInfoExtended.isChunkReceived.resize(fileInfo.second.nChunks);
|
||||
fileInfoExtended.isChunkRequested.resize(fileInfo.second.nChunks);
|
||||
}
|
||||
@@ -1858,7 +1860,7 @@ void renderMain() {
|
||||
ImGui::Text("%s", "");
|
||||
}
|
||||
|
||||
if ((fileInfoExtended.isReceiving == false || isReceived) && fileInfoExtended.requestToShare == false) {
|
||||
if ((fileInfoExtended.receiving == false || isReceived) && fileInfoExtended.requestToShare == false) {
|
||||
ImGui::SameLine();
|
||||
if (ImGui::Button(ICON_FA_TRASH " Clear")) {
|
||||
toErase = fileInfo.first;
|
||||
@@ -2034,7 +2036,7 @@ void renderMain() {
|
||||
}
|
||||
auto wSize = ImGui::GetContentRegionAvail();
|
||||
ImGui::PushStyleColor(ImGuiCol_FrameBg, { 0.3f, 0.3f, 0.3f, 0.3f });
|
||||
if (statsCurrent.isReceiving) {
|
||||
if (statsCurrent.receiving) {
|
||||
ImGui::PushStyleColor(ImGuiCol_PlotHistogram, { 1.0f, 0.0f, 0.0f, 1.0f });
|
||||
} else {
|
||||
ImGui::PushStyleColor(ImGuiCol_PlotHistogram, { 0.0f, 1.0f, 0.0f, 1.0f });
|
||||
|
||||
Reference in New Issue
Block a user