diff --git a/src/gui/gui.cpp b/src/gui/gui.cpp index a262b9da2..430d2845e 100644 --- a/src/gui/gui.cpp +++ b/src/gui/gui.cpp @@ -7102,8 +7102,11 @@ FurnaceGUI::FurnaceGUI(): displayInternalPorts(false), subPortPos(0.0f,0.0f), oscTotal(0), + oscWidth(512), oscZoom(0.5f), oscWindowSize(20.0f), + oscInput(0.0f), + oscInput1(0.0f), oscZoomSlider(false), chanOscCols(3), chanOscAutoColsType(0), @@ -7217,7 +7220,7 @@ FurnaceGUI::FurnaceGUI(): memset(patChanX,0,sizeof(float)*(DIV_MAX_CHANS+1)); memset(patChanSlideY,0,sizeof(float)*(DIV_MAX_CHANS+1)); memset(lastIns,-1,sizeof(int)*DIV_MAX_CHANS); - memset(oscValues,0,sizeof(float)*512); + memset(oscValues,0,sizeof(float)*1024); memset(chanOscLP0,0,sizeof(float)*DIV_MAX_CHANS); memset(chanOscLP1,0,sizeof(float)*DIV_MAX_CHANS); diff --git a/src/gui/gui.h b/src/gui/gui.h index 101247dc0..044e15767 100644 --- a/src/gui/gui.h +++ b/src/gui/gui.h @@ -1969,10 +1969,11 @@ class FurnaceGUI { ImVec2 subPortPos; // oscilloscope - int oscTotal; - float oscValues[512]; + int oscTotal, oscWidth; + float oscValues[1024]; float oscZoom; float oscWindowSize; + float oscInput, oscInput1; bool oscZoomSlider; // per-channel oscilloscope diff --git a/src/gui/osc.cpp b/src/gui/osc.cpp index 7f783ddee..5e3e88a9b 100644 --- a/src/gui/osc.cpp +++ b/src/gui/osc.cpp @@ -20,6 +20,8 @@ #include "gui.h" #include "imgui_internal.h" #include +#include "../ta-log.h" +#include "../engine/filter.h" void FurnaceGUI::readOsc() { int writePos=e->oscWritePos; @@ -45,21 +47,81 @@ void FurnaceGUI::readOsc() { if (total>avail) total=avail; //printf("total: %d. avail: %d bias: %d\n",total,avail,bias); + memset(oscValues,0,1024*sizeof(float)); + int winSize=e->getAudioDescGot().rate*(oscWindowSize/1000.0); int oscReadPos=(writePos-winSize)&0x7fff; - for (int i=0; i<512; i++) { - int pos=(oscReadPos+(i*winSize/512))&0x7fff; - oscValues[i]=0; - for (int j=0; jgetAudioDescGot().outChans; j++) { - oscValues[i]+=e->oscBuf[j][pos]; - } - oscValues[i]/=e->getAudioDescGot().outChans; - if (oscValues[i]>0.001f || oscValues[i]<-0.001f) { - WAKE_UP; + float* sincITable=DivFilterTables::getSincIntegralTable(); + + float posFrac=0.0; + int posInt=oscReadPos; + float factor=(float)oscWidth/(float)winSize; + for (int i=0; igetAudioDescGot().outChans; j++) { + avg+=e->oscBuf[j][posInt&0x7fff]; + } + avg/=e->getAudioDescGot().outChans; + oscValues[i]+=avg; + + posFrac+=1.0; + while (posFrac>=1.0) { + unsigned int n=((unsigned int)(posFrac*8192.0))&8191; + posFrac-=factor; + posInt++; + + prevAvg=avg; + avg=0.0f; + for (int j=0; jgetAudioDescGot().outChans; j++) { + avg+=e->oscBuf[j][posInt&0x7fff]; + } + avg/=e->getAudioDescGot().outChans; + + float* t1=&sincITable[(8191-n)<<3]; + float* t2=&sincITable[n<<3]; + float delta=avg-prevAvg; + + for (int j=0; j<8; j++) { + if (i-j>0) { + oscValues[i-j]+=t1[j]*-delta; + } + if (i+j+1getAudioDescGot().outChans; j++) { + avg+=e->oscBuf[j][pos]; + } + avg/=e->getAudioDescGot().outChans; + + //oscInput+=(avg-oscInput)*cut; + //oscInput1+=(oscInput1-oscInput)*cut; + + oscInput=avg; + + for (int j=(i*oscWidth)/winSize; j<((i+1)*oscWidth)/winSize; j++) { + if (j>=oscWidth) break; + oscValues[j]=oscInput; + } + + if (avg>0.001f || avg<-0.001f) { + WAKE_UP; + } + }*/ + + /*for (int i=0; igetAudioDescGot().outChans; i++) { peak[i]*=1.0-peakDecay; @@ -124,7 +186,7 @@ void FurnaceGUI::drawOsc() { ImDrawList* dl=ImGui::GetWindowDrawList(); ImGuiWindow* window=ImGui::GetCurrentWindow(); - ImVec2 waveform[512]; + ImVec2 waveform[1024]; ImVec2 size=ImGui::GetContentRegionAvail(); ImVec2 minArea=window->DC.CursorPos; @@ -211,8 +273,12 @@ void FurnaceGUI::drawOsc() { dpiScale ); - for (size_t i=0; i<512; i++) { - float x=(float)i/512.0f; + oscWidth=round(inRect.Max.x-inRect.Min.x); + if (oscWidth<1) oscWidth=1; + if (oscWidth>1024) oscWidth=1024; + + for (int i=0; iFlags; + //dl->Flags&=~(ImDrawListFlags_AntiAliasedLines|ImDrawListFlags_AntiAliasedLinesUseTex); if (settings.oscEscapesBoundary) { dl->PushClipRectFullScreen(); - dl->AddPolyline(waveform,512,color,ImDrawFlags_None,dpiScale); + dl->AddPolyline(waveform,oscWidth,color,ImDrawFlags_None,dpiScale); dl->PopClipRect(); } else { - dl->AddPolyline(waveform,512,color,ImDrawFlags_None,dpiScale); + dl->AddPolyline(waveform,oscWidth,color,ImDrawFlags_None,dpiScale); } + //dl->Flags=prevFlags; if (settings.oscBorder) { dl->AddRect(inRect.Min,inRect.Max,borderColor,settings.oscRoundedCorners?(8.0f*dpiScale):0.0f,0,1.5f*dpiScale); }