phase plot, amplitude control, display pause
This commit is contained in:
parent
edef2a971a
commit
d4f82af207
75
sndlock.cpp
75
sndlock.cpp
@ -24,10 +24,13 @@
|
|||||||
|
|
||||||
static std::atomic<bool> shutdown_threads;
|
static std::atomic<bool> shutdown_threads;
|
||||||
static std::atomic<double> frequency[SND_PCHAN];
|
static std::atomic<double> frequency[SND_PCHAN];
|
||||||
|
static std::atomic<double> amplitude[SND_PCHAN];
|
||||||
static std::atomic<double> lpf_bandwidth[SND_PCHAN];
|
static std::atomic<double> lpf_bandwidth[SND_PCHAN];
|
||||||
|
|
||||||
static std::mutex lpf_hist_mutex;
|
static std::mutex li_hist_mutex;
|
||||||
static float lpf_hist[SND_PCHAN][512];
|
static std::atomic<bool> li_hist_pause[SND_PCHAN];
|
||||||
|
static float li_hist_mag[SND_PCHAN][512];
|
||||||
|
static float li_hist_phase[SND_PCHAN][512];
|
||||||
|
|
||||||
static void dsp_thread()
|
static void dsp_thread()
|
||||||
{
|
{
|
||||||
@ -77,7 +80,7 @@ static void dsp_thread()
|
|||||||
for(int i=0;i<SND_PCHAN;i++)
|
for(int i=0;i<SND_PCHAN;i++)
|
||||||
// input channels are averaged together to reduce uncorrelated noise
|
// input channels are averaged together to reduce uncorrelated noise
|
||||||
lockin[i].set_scale(pow(0.5, SND_BITS-1)/SND_RCHAN);
|
lockin[i].set_scale(pow(0.5, SND_BITS-1)/SND_RCHAN);
|
||||||
int lpf_count[SND_PCHAN] = { 0 };
|
int li_count[SND_PCHAN] = { 0 };
|
||||||
|
|
||||||
nfds_t nfds = sio_nfds(hdl);
|
nfds_t nfds = sio_nfds(hdl);
|
||||||
struct pollfd pfd[nfds];
|
struct pollfd pfd[nfds];
|
||||||
@ -90,7 +93,6 @@ static void dsp_thread()
|
|||||||
lockin[i].set_bandwidth(lpf_bandwidth[i]/SND_RATE);
|
lockin[i].set_bandwidth(lpf_bandwidth[i]/SND_RATE);
|
||||||
|
|
||||||
if(revents & POLLOUT) {
|
if(revents & POLLOUT) {
|
||||||
double scale = pow(2.0, SND_BITS-1) - 1.0;
|
|
||||||
if(buf_out_offset == sizeof(buf_out)) {
|
if(buf_out_offset == sizeof(buf_out)) {
|
||||||
for(int i=0;i<SND_PCHAN;i++) {
|
for(int i=0;i<SND_PCHAN;i++) {
|
||||||
phase_t ftw = frequency_to_ftw(frequency[i]/SND_RATE);
|
phase_t ftw = frequency_to_ftw(frequency[i]/SND_RATE);
|
||||||
@ -98,9 +100,11 @@ static void dsp_thread()
|
|||||||
if(!ftw_fifo[i].push(ftw))
|
if(!ftw_fifo[i].push(ftw))
|
||||||
std::cerr << "FTW FIFO overflow" << std::endl;
|
std::cerr << "FTW FIFO overflow" << std::endl;
|
||||||
}
|
}
|
||||||
for(int i=0;i<SND_PCHAN;i++)
|
for(int i=0;i<SND_PCHAN;i++) {
|
||||||
|
double scale = amplitude[i]*(pow(2.0, SND_BITS-1) - 1.0);
|
||||||
for(int j=0;j<SND_BUFLEN;j++)
|
for(int j=0;j<SND_BUFLEN;j++)
|
||||||
buf_out[SND_PCHAN*j+i] = scale*dds[i].get();
|
buf_out[SND_PCHAN*j+i] = scale*dds[i].get();
|
||||||
|
}
|
||||||
buf_out_offset = 0;
|
buf_out_offset = 0;
|
||||||
}
|
}
|
||||||
size_t written = sio_write(hdl, (const char *)buf_out + buf_out_offset, sizeof(buf_out) - buf_out_offset);
|
size_t written = sio_write(hdl, (const char *)buf_out + buf_out_offset, sizeof(buf_out) - buf_out_offset);
|
||||||
@ -125,14 +129,18 @@ static void dsp_thread()
|
|||||||
double sample = 0.0;
|
double sample = 0.0;
|
||||||
for(int k=0;k<SND_RCHAN;k++)
|
for(int k=0;k<SND_RCHAN;k++)
|
||||||
sample += (double)buf_in[SND_RCHAN*j+k];
|
sample += (double)buf_in[SND_RCHAN*j+k];
|
||||||
double mag = std::abs(lockin[i].update(sample));
|
std::complex<double> lockin_out = lockin[i].update(sample);
|
||||||
|
|
||||||
lpf_count[i]++;
|
if(!li_hist_pause[i]) {
|
||||||
if(lpf_count[i] == 200) {
|
li_count[i]++;
|
||||||
lpf_count[i] = 0;
|
if(li_count[i] == 200) {
|
||||||
std::lock_guard<std::mutex> guard(lpf_hist_mutex);
|
li_count[i] = 0;
|
||||||
std::memmove(&lpf_hist[i][0], &lpf_hist[i][1], 511*sizeof(float));
|
std::lock_guard<std::mutex> guard(li_hist_mutex);
|
||||||
lpf_hist[i][511] = mag;
|
std::memmove(&li_hist_mag[i][0], &li_hist_mag[i][1], 511*sizeof(float));
|
||||||
|
li_hist_mag[i][511] = std::abs(lockin_out);
|
||||||
|
std::memmove(&li_hist_phase[i][0], &li_hist_phase[i][1], 511*sizeof(float));
|
||||||
|
li_hist_phase[i][511] = std::arg(lockin_out);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -157,7 +165,7 @@ int main(int argc, char* argv[])
|
|||||||
std::atexit(glfwTerminate);
|
std::atexit(glfwTerminate);
|
||||||
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
|
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
|
||||||
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 0);
|
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 0);
|
||||||
static GLFWwindow* window = glfwCreateWindow(1024, 768, "sndlock", nullptr, nullptr);
|
static GLFWwindow* window = glfwCreateWindow(1024, 1200, "sndlock", nullptr, nullptr);
|
||||||
if(window == nullptr) {
|
if(window == nullptr) {
|
||||||
std::cerr << "failed to create GLFW window" << std::endl;
|
std::cerr << "failed to create GLFW window" << std::endl;
|
||||||
return 1;
|
return 1;
|
||||||
@ -185,6 +193,7 @@ int main(int argc, char* argv[])
|
|||||||
|
|
||||||
for(int i=0;i<SND_PCHAN;i++) {
|
for(int i=0;i<SND_PCHAN;i++) {
|
||||||
frequency[i] = 441.0 + 202.0*i;
|
frequency[i] = 441.0 + 202.0*i;
|
||||||
|
amplitude[i] = 1.0;
|
||||||
lpf_bandwidth[i] = 10.0;
|
lpf_bandwidth[i] = 10.0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -200,11 +209,10 @@ int main(int argc, char* argv[])
|
|||||||
};
|
};
|
||||||
std::atexit(SetShutdown);
|
std::atexit(SetShutdown);
|
||||||
|
|
||||||
bool exit = false;
|
|
||||||
float plot_scale[SND_PCHAN];
|
float plot_scale[SND_PCHAN];
|
||||||
for(int i=0;i<SND_PCHAN;i++)
|
for(int i=0;i<SND_PCHAN;i++)
|
||||||
plot_scale[i] = 0.005f;
|
plot_scale[i] = 0.05f;
|
||||||
while(!exit && !glfwWindowShouldClose(window)) {
|
while(!glfwWindowShouldClose(window)) {
|
||||||
glfwPollEvents();
|
glfwPollEvents();
|
||||||
glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
|
glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
|
||||||
glClear(GL_COLOR_BUFFER_BIT);
|
glClear(GL_COLOR_BUFFER_BIT);
|
||||||
@ -218,37 +226,52 @@ int main(int argc, char* argv[])
|
|||||||
ImGui::PushStyleVar(ImGuiStyleVar_WindowRounding, 0.0f);
|
ImGui::PushStyleVar(ImGuiStyleVar_WindowRounding, 0.0f);
|
||||||
ImGui::Begin("sndlock", nullptr, ImGuiWindowFlags_NoDecoration | ImGuiWindowFlags_NoResize);
|
ImGui::Begin("sndlock", nullptr, ImGuiWindowFlags_NoDecoration | ImGuiWindowFlags_NoResize);
|
||||||
|
|
||||||
if(ImGui::CollapsingHeader("Modulation", ImGuiTreeNodeFlags_DefaultOpen)) {
|
if(ImGui::CollapsingHeader("Modulation")) {
|
||||||
for(int i=0;i<SND_PCHAN;i++) {
|
for(int i=0;i<SND_PCHAN;i++) {
|
||||||
ImGui::Text("Channel %d", i);
|
|
||||||
char str[64];
|
char str[64];
|
||||||
|
sprintf(str, "Channel %d", i);
|
||||||
|
ImGui::SeparatorText(str);
|
||||||
sprintf(str, "frequency##%d", i);
|
sprintf(str, "frequency##%d", i);
|
||||||
float frequency_l = frequency[i];
|
float frequency_l = frequency[i];
|
||||||
ImGui::SliderFloat(str, &frequency_l, 50.0f, 8000.0f);
|
ImGui::SliderFloat(str, &frequency_l, 50.0f, 8000.0f);
|
||||||
frequency[i] = frequency_l;
|
frequency[i] = frequency_l;
|
||||||
|
sprintf(str, "amplitude##%d", i);
|
||||||
|
float amplitude_l = amplitude[i];
|
||||||
|
ImGui::SliderFloat(str, &litude_l, 0.0f, 1.0f);
|
||||||
|
amplitude[i] = amplitude_l;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if(ImGui::CollapsingHeader("Demodulation", ImGuiTreeNodeFlags_DefaultOpen)) {
|
if(ImGui::CollapsingHeader("Demodulation", ImGuiTreeNodeFlags_DefaultOpen)) {
|
||||||
for(int i=0;i<SND_PCHAN;i++) {
|
for(int i=0;i<SND_PCHAN;i++) {
|
||||||
char str[64];
|
char str[64];
|
||||||
|
|
||||||
ImGui::Text("Channel %d", i);
|
sprintf(str, "Channel %d", i);
|
||||||
|
ImGui::SeparatorText(str);
|
||||||
sprintf(str, "LPF BW##%d", i);
|
sprintf(str, "LPF BW##%d", i);
|
||||||
float lpf_bandwidth_l = lpf_bandwidth[i];
|
float lpf_bandwidth_l = lpf_bandwidth[i];
|
||||||
ImGui::SliderFloat(str, &lpf_bandwidth_l, 0.5f, 200.0f);
|
ImGui::SliderFloat(str, &lpf_bandwidth_l, 0.5f, 200.0f);
|
||||||
lpf_bandwidth[i] = lpf_bandwidth_l;
|
lpf_bandwidth[i] = lpf_bandwidth_l;
|
||||||
|
|
||||||
sprintf(str, "plot scale##%d", i);
|
sprintf(str, "mag scale##%d", i);
|
||||||
ImGui::SliderFloat(str, &plot_scale[i], 0.001f, 0.01f);
|
ImGui::SliderFloat(str, &plot_scale[i], 0.01f, 0.1f);
|
||||||
sprintf(str, "output##%d", i);
|
|
||||||
{
|
{
|
||||||
std::lock_guard<std::mutex> guard(lpf_hist_mutex);
|
std::lock_guard<std::mutex> guard(li_hist_mutex);
|
||||||
ImGui::PlotLines(str, lpf_hist[i], 512, 0, 0, -0.0f, plot_scale[i], ImVec2(0.0f, 200.0f));
|
sprintf(str, "magnitude##%d", i);
|
||||||
|
ImGui::PlotLines(str, li_hist_mag[i], 512, 0, 0, -0.0f, 0.1f*plot_scale[i], ImVec2(0.0f, 200.0f));
|
||||||
|
sprintf(str, "phase##%d", i);
|
||||||
|
ImGui::PlotLines(str, li_hist_phase[i], 512, 0, 0, -M_PI, M_PI, ImVec2(0.0f, 200.0f));
|
||||||
|
}
|
||||||
|
bool pause_l = li_hist_pause[i];
|
||||||
|
sprintf(str, "pause##%d", i);
|
||||||
|
ImGui::Checkbox(str, &pause_l);
|
||||||
|
li_hist_pause[i] = pause_l;
|
||||||
|
ImGui::SameLine();
|
||||||
|
{
|
||||||
|
std::lock_guard<std::mutex> guard(li_hist_mutex);
|
||||||
|
ImGui::Text("values: %8.5f %8.5f rad", li_hist_mag[i][511], li_hist_phase[i][511]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if(ImGui::Button("Exit"))
|
|
||||||
exit = true;
|
|
||||||
|
|
||||||
ImGui::End();
|
ImGui::End();
|
||||||
ImGui::PopStyleVar(1);
|
ImGui::PopStyleVar(1);
|
||||||
|
Loading…
Reference in New Issue
Block a user