diff --git a/Builds/Linux/Makefile b/Builds/Linux/Makefile index 8a3daf440e6c62c8647fbc3fcce808d6fa91dfec..981f776caa43b3bdb8b7dc05a262c3c58c7207d0 100644 --- a/Builds/Linux/Makefile +++ b/Builds/Linux/Makefile @@ -19,7 +19,7 @@ ifeq ($(CONFIG),Debug) OUTDIR := build CPPFLAGS := $(DEPFLAGS) -D "LINUX=1" -D "DEBUG=1" -D "_DEBUG=1" -D "JUCER_LINUX_MAKE_7346DA2A=1" -I "/usr/include" -I "/usr/include/freetype2" CFLAGS += $(CPPFLAGS) $(TARGET_ARCH) -g -ggdb -O0 - CXXFLAGS += $(CFLAGS) -export-dynamic -g + CXXFLAGS += $(CFLAGS) -export-dynamic LDFLAGS += -L$(BINDIR) -L$(LIBDIR) -L"/usr/X11R6/lib/" -L"../../JuceLibraryCode/bin" -lfreetype -lpthread -lrt -lX11 -lGL -lGLU -lXinerama -lasound -lftdi -lftgl LDDEPS := RESFLAGS := -D "LINUX=1" -D "DEBUG=1" -D "_DEBUG=1" -D "JUCER_LINUX_MAKE_7346DA2A=1" -I "/usr/include" -I "/usr/include/freetype2" @@ -34,7 +34,7 @@ ifeq ($(CONFIG),Release) OUTDIR := build CPPFLAGS := $(DEPFLAGS) -D "LINUX=1" -D "NDEBUG=1" -D "JUCER_LINUX_MAKE_7346DA2A=1" -I "/usr/include" -I "/usr/include/freetype2" CFLAGS += $(CPPFLAGS) $(TARGET_ARCH) -O3 - CXXFLAGS += $(CFLAGS) -export-dynamic -g + CXXFLAGS += $(CFLAGS) -export-dynamic LDFLAGS += -L$(BINDIR) -L$(LIBDIR) -L"/usr/X11R6/lib/" -L"../../JuceLibraryCode/bin" -lfreetype -lpthread -lrt -lX11 -lGL -lGLU -lXinerama -lasound -lftdi -lftgl LDDEPS := RESFLAGS := -D "LINUX=1" -D "NDEBUG=1" -D "JUCER_LINUX_MAKE_7346DA2A=1" -I "/usr/include" -I "/usr/include/freetype2" @@ -68,6 +68,7 @@ OBJECTS := \ $(OBJDIR)/LfpDisplayNode_30ef22fd.o \ $(OBJDIR)/Merger_2f90542e.o \ $(OBJDIR)/Splitter_6e27a57b.o \ + $(OBJDIR)/StereotrodePlot_4710b8f1.o \ $(OBJDIR)/ElectrodePlot_7a206ec4.o \ $(OBJDIR)/BaseUIElement_ec903c4d.o \ $(OBJDIR)/GenericAxes_d802ed92.o \ @@ -273,6 +274,11 @@ $(OBJDIR)/Splitter_6e27a57b.o: ../../Source/Processors/Utilities/Splitter.cpp @echo "Compiling Splitter.cpp" @$(CXX) $(CXXFLAGS) -o "$@" -c "$<" +$(OBJDIR)/StereotrodePlot_4710b8f1.o: ../../Source/Processors/Visualization/SpikePlotting/StereotrodePlot.cpp + -@mkdir -p $(OBJDIR) + @echo "Compiling StereotrodePlot.cpp" + @$(CXX) $(CXXFLAGS) -o "$@" -c "$<" + $(OBJDIR)/ElectrodePlot_7a206ec4.o: ../../Source/Processors/Visualization/SpikePlotting/ElectrodePlot.cpp -@mkdir -p $(OBJDIR) @echo "Compiling ElectrodePlot.cpp" diff --git a/Builds/MacOSX/open-ephys.xcodeproj/project.pbxproj b/Builds/MacOSX/open-ephys.xcodeproj/project.pbxproj index 61e194bb64875484e0092bb2d10b0016bb8e29bd..5a72e805410e0a28e78f1eaf47d1a4846c39bc82 100644 --- a/Builds/MacOSX/open-ephys.xcodeproj/project.pbxproj +++ b/Builds/MacOSX/open-ephys.xcodeproj/project.pbxproj @@ -42,6 +42,7 @@ F1268EC5E783EC8ECEBCA5D3 = { isa = PBXBuildFile; fileRef = 5935F823A2EE45AC36A0201F; }; 4A00153E1E69A74BC6B7D8A6 = { isa = PBXBuildFile; fileRef = 3973173C7FA07073B4F86B29; }; 5F13B8FFB1584BFF6C05AD39 = { isa = PBXBuildFile; fileRef = 9A47B52E5E1CD17DC9C72B53; }; + B11D72764B1B17BF2B8C6E67 = { isa = PBXBuildFile; fileRef = C92B3F413B0F24752ADE6730; }; 938FC2F779C2CF4B8C7ECFFE = { isa = PBXBuildFile; fileRef = 3BB44F767E701E3642435FA0; }; 55A240CCFCD604CA8DF8FC8C = { isa = PBXBuildFile; fileRef = 41591F74A761BAC908FA8AD8; }; 8025F04ED261C7F7D2DC0F06 = { isa = PBXBuildFile; fileRef = 24C6D768C87E1C42C644C4BD; }; @@ -204,6 +205,8 @@ 7977CAB4A151C41F4140FE1A = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = Merger.h; path = ../../Source/Processors/Utilities/Merger.h; sourceTree = "SOURCE_ROOT"; }; 9A47B52E5E1CD17DC9C72B53 = { isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; name = Splitter.cpp; path = ../../Source/Processors/Utilities/Splitter.cpp; sourceTree = "SOURCE_ROOT"; }; B92E8189F69E0B926C73B654 = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = Splitter.h; path = ../../Source/Processors/Utilities/Splitter.h; sourceTree = "SOURCE_ROOT"; }; + C92B3F413B0F24752ADE6730 = { isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; name = StereotrodePlot.cpp; path = ../../Source/Processors/Visualization/SpikePlotting/StereotrodePlot.cpp; sourceTree = "SOURCE_ROOT"; }; + FDD549F527C378CF36BDB8C7 = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = StereotrodePlot.h; path = ../../Source/Processors/Visualization/SpikePlotting/StereotrodePlot.h; sourceTree = "SOURCE_ROOT"; }; 3BB44F767E701E3642435FA0 = { isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; name = ElectrodePlot.cpp; path = ../../Source/Processors/Visualization/SpikePlotting/ElectrodePlot.cpp; sourceTree = "SOURCE_ROOT"; }; 1AAF672654B16469EFB41AC2 = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = ElectrodePlot.h; path = ../../Source/Processors/Visualization/SpikePlotting/ElectrodePlot.h; sourceTree = "SOURCE_ROOT"; }; 41591F74A761BAC908FA8AD8 = { isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; name = BaseUIElement.cpp; path = ../../Source/Processors/Visualization/SpikePlotting/BaseUIElement.cpp; sourceTree = "SOURCE_ROOT"; }; @@ -423,6 +426,8 @@ 9A47B52E5E1CD17DC9C72B53, B92E8189F69E0B926C73B654 ); name = Utilities; sourceTree = "<group>"; }; 1255E9B28ADAA1A1CADC4A6E = { isa = PBXGroup; children = ( + C92B3F413B0F24752ADE6730, + FDD549F527C378CF36BDB8C7, 3BB44F767E701E3642435FA0, 1AAF672654B16469EFB41AC2, 41591F74A761BAC908FA8AD8, @@ -694,6 +699,7 @@ F1268EC5E783EC8ECEBCA5D3, 4A00153E1E69A74BC6B7D8A6, 5F13B8FFB1584BFF6C05AD39, + B11D72764B1B17BF2B8C6E67, 938FC2F779C2CF4B8C7ECFFE, 55A240CCFCD604CA8DF8FC8C, 8025F04ED261C7F7D2DC0F06, diff --git a/Source/Processors/SpikeDisplayNode.cpp b/Source/Processors/SpikeDisplayNode.cpp index cc33126e3e9455ef8c4ce4a1d0646850ef55e209..7529f7ff51273e6786643f398a540f5edfdc3172 100644 --- a/Source/Processors/SpikeDisplayNode.cpp +++ b/Source/Processors/SpikeDisplayNode.cpp @@ -86,7 +86,8 @@ void SpikeDisplayNode::setParameter (int parameterIndex, float newValue) void SpikeDisplayNode::process(AudioSampleBuffer &buffer, MidiBuffer &midiMessages, int& nSamples) { - std::cout<<"SpikeDisplayNode::process"<<std::endl; + //std::cout<<"SpikeDisplayNode::process"<<std::endl; + /* uint64_t ts = 00000; int noise = 10; SpikeObject newSpike; @@ -95,11 +96,12 @@ void SpikeDisplayNode::process(AudioSampleBuffer &buffer, MidiBuffer &midiMessag spikebuffer.push(newSpike); bufferSize++; - + */ } bool SpikeDisplayNode::getNextSpike(SpikeObject *spike){ std::cout<<"SpikeDisplayNode::getNextSpike()"<<std::endl; + /* if (bufferSize<1 || spikebuffer.empty()) return false; else{ @@ -109,6 +111,7 @@ bool SpikeDisplayNode::getNextSpike(SpikeObject *spike){ *spike = s; return true; } - + */ return false; + } \ No newline at end of file diff --git a/Source/Processors/Visualization/SpikeDisplayCanvas.cpp b/Source/Processors/Visualization/SpikeDisplayCanvas.cpp index cd771d04b3e0899cba59d0ba5693c4d1e8e68056..f934eaa5279c62a0ac65b4a229d41595ead9df7a 100644 --- a/Source/Processors/Visualization/SpikeDisplayCanvas.cpp +++ b/Source/Processors/Visualization/SpikeDisplayCanvas.cpp @@ -24,7 +24,7 @@ #include "SpikeDisplayCanvas.h" SpikeDisplayCanvas::SpikeDisplayCanvas(SpikeDisplayNode* n) : processor(n), - xBuffer(0), yBuffer(0), newSpike(false) + xBuffer(0), yBuffer(0), newSpike(false) { @@ -41,11 +41,8 @@ SpikeDisplayCanvas::SpikeDisplayCanvas(SpikeDisplayNode* n) : processor(n), //generateEmptySpike(&spike, 1); - for (int i=0; i<8; i++) - { - ElectrodePlot ep = ElectrodePlot(10 +i * 80, 10, 75, 75, ""); - plots.push_back(ep); - } + initializeSpikePlots(); + // displayBuffer = processor->getDisplayBufferAddress(); // displayBufferSize = displayBuffer->getNumSamples(); // std::cout << "Setting displayBufferSize on SpikeDisplayCanvas to " << displayBufferSize << std::endl; @@ -53,15 +50,34 @@ SpikeDisplayCanvas::SpikeDisplayCanvas(SpikeDisplayNode* n) : processor(n), // totalHeight = (plotHeight+yBuffer)*nChans + yBuffer; - // screenBuffer = new AudioSampleBuffer(nChans, 10000); - + // screenBuffer = new AudioSampleBuffer(nChans, 10000); } SpikeDisplayCanvas::~SpikeDisplayCanvas() { + +} + +void SpikeDisplayCanvas::initializeSpikePlots(){ + std::cout<<"Initializing Plots"<<std::endl; + int xPadding = 10; + int yPadding = 10; + + int nPlots = 4; + + int totalWidth = 900; // This is a hack the width as the width isn't known before its drawn + + int plotWidth = (totalWidth - (nPlots + 1 ) * xPadding) / nPlots; + int plotHeight = plotWidth / 2; + for (int i=0; i<nPlots; i++) + { + StereotrodePlot p = StereotrodePlot( xPadding + i * (plotWidth + xPadding) , yPadding, plotWidth, plotHeight, ""); + plots.push_back(p); + } } + void SpikeDisplayCanvas::newOpenGLContextCreated() { @@ -162,8 +178,8 @@ void SpikeDisplayCanvas::renderOpenGL() } //} - - drawScrollBars(); + //std::cout << getHeight()<<" "<< getTotalHeight()<<" "<<std::endl; + drawScrollBars(); } void SpikeDisplayCanvas::drawTicks() diff --git a/Source/Processors/Visualization/SpikeDisplayCanvas.h b/Source/Processors/Visualization/SpikeDisplayCanvas.h index 11647624f4576847e341edeaca2f74c24da12ac5..192ac8ee64540b2156373d57513619b02fffcd78 100644 --- a/Source/Processors/Visualization/SpikeDisplayCanvas.h +++ b/Source/Processors/Visualization/SpikeDisplayCanvas.h @@ -27,6 +27,7 @@ #include "../SpikeDisplayNode.h" #include "SpikePlotting/ElectrodePlot.h" +#include "SpikePlotting/StereotrodePlot.h" #include "SpikeObject.h" #include "Visualizer.h" @@ -63,7 +64,7 @@ private: bool newSpike; SpikeObject spike; SpikeDisplayNode* processor; - std::vector<ElectrodePlot> plots; + std::vector<StereotrodePlot> plots; // AudioSampleBuffer* displayBuffer; // ScopedPointer<AudioSampleBuffer> screenBuffer; // MidiBuffer* eventBuffer; diff --git a/Source/Processors/Visualization/SpikeObject.cpp b/Source/Processors/Visualization/SpikeObject.cpp index 9f4130b3858cc76d60223387e4064f7364e0bb9e..dc8ff7f5ba029dec3cfa5ab55e0ae30467a6cacb 100644 --- a/Source/Processors/Visualization/SpikeObject.cpp +++ b/Source/Processors/Visualization/SpikeObject.cpp @@ -134,7 +134,7 @@ void makeBufferValid(char *buffer, int bufferSize){ void generateSimulatedSpike(SpikeObject *s, uint64_t timestamp, int noise) { - std::cout<<"generateSimulatedSpike()"<<std::endl; + //std::cout<<"generateSimulatedSpike()"<<std::endl; uint16_t trace[][32] = { diff --git a/Source/Processors/Visualization/SpikePlotting/ElectrodePlot.cpp b/Source/Processors/Visualization/SpikePlotting/ElectrodePlot.cpp index e3d577604294c5c77e5b5f60fa625dcf6d4932ca..b86a8c5117e108ef01b93d6b4249dc95e763d6e3 100644 --- a/Source/Processors/Visualization/SpikePlotting/ElectrodePlot.cpp +++ b/Source/Processors/Visualization/SpikePlotting/ElectrodePlot.cpp @@ -1,5 +1,6 @@ #include "ElectrodePlot.h" #include "../SpikeObject.h" +#include "PlotUtils.h" ElectrodePlot::ElectrodePlot(): BaseUIElement(), titleHeight(0), enableTitle(true), limitsChanged(true) @@ -27,7 +28,7 @@ ElectrodePlot::~ElectrodePlot(){ // the right direction void ElectrodePlot::redraw(){ - std::cout<<"ElectrodePlot() starting drawing"<<std::endl;\ + //std::cout<<"ElectrodePlot() starting drawing"<<std::endl;\ BaseUIElement::clearNextDraw = true; BaseUIElement::redraw(); @@ -36,7 +37,7 @@ void ElectrodePlot::redraw(){ // This would normally happen for collection of axes but an electrode plot doesn't have a collection instead its a single axes void ElectrodePlot::processSpikeObject(SpikeObject s){ - std::cout<<"ElectrdePlot::processSpikeObject()"<<std::endl; + //std::cout<<"ElectrdePlot::processSpikeObject()"<<std::endl; axes.updateSpikeData(s); } void ElectrodePlot::setTitle(char *n){ @@ -64,7 +65,7 @@ void ElectrodePlot::initAxes(){ double axesHeight = (BaseUIElement::height - titleHeight); - axes = WaveAxes(minX, minY, axesWidth, axesHeight, 0); + axes = WaveAxes(minX, minY, axesWidth, axesHeight, WAVE1); //axes.setEnabled(false); axes.setYLims(-1*pow(2,11), pow(2,14)*1.6); diff --git a/Source/Processors/Visualization/SpikePlotting/ElectrodePlot.h b/Source/Processors/Visualization/SpikePlotting/ElectrodePlot.h index 5db97f504930164707addcdb9db45562421f5c03..791ddbcc617b68f4514abab12687c5ef3abbc7c7 100644 --- a/Source/Processors/Visualization/SpikePlotting/ElectrodePlot.h +++ b/Source/Processors/Visualization/SpikePlotting/ElectrodePlot.h @@ -33,7 +33,8 @@ class ElectrodePlot : public BaseUIElement{ double limits[1][2]; WaveAxes axes; - + + // void zoomAxes(int n, bool xdim, int zoomval); // void zoomProjection (int n, bool xdim, int zoomval); diff --git a/Source/Processors/Visualization/SpikePlotting/GenericAxes.cpp b/Source/Processors/Visualization/SpikePlotting/GenericAxes.cpp index 738974895318f38b2d5073ead6a9a2e037a45150..db3904e49a80078dd2c0c5b9412a0c59962cc84a 100644 --- a/Source/Processors/Visualization/SpikePlotting/GenericAxes.cpp +++ b/Source/Processors/Visualization/SpikePlotting/GenericAxes.cpp @@ -8,8 +8,6 @@ GenericAxes::GenericAxes(): { ylims[0] = 0; ylims[1] = 1; - - //BaseUIElement::elementName = (char*) "GenericAxes"; } GenericAxes::GenericAxes(int x, int y, double w, double h, int t): @@ -17,61 +15,17 @@ GenericAxes::GenericAxes(int x, int y, double w, double h, int t): gotFirstSpike(false), resizedFlag(false) { - std::cout<<"Generic Axes!!!!!"<<std::endl; - std::cout<<"gotFirstSpike:"<<gotFirstSpike<<std::endl; - // if (t<WAVE1 || t>PROJ3x4) - //("Invalid Axes type specified"); type = t; - -// BaseUIElement::elementName = (char*) "GenericAxes"; - } void GenericAxes::updateSpikeData(SpikeObject newSpike){ - - std::cout<<"GenericAxes::updateSpikeData() "; if (!gotFirstSpike){ gotFirstSpike = true; } s = newSpike; - std::cout<<"got spike with nSamples:"<<s.nSamples<<std::endl; } -// void GenericAxes::redraw(){ -// BaseUIElement::redraw(); -// if (BaseUIElement::enabled) -// plotData(); - -// BaseUIElement::drawElementEdges(); -// } -// void GenericAxes::plotData(){ -// if (!gotFirstSpike) -// { -// std::cout<<"\tWaiting for the first spike"<<std::endl; -// return; -// } -// switch(type){ -// case WAVE1: -// case WAVE2: -// case WAVE3: -// case WAVE4: -// plotWaveform(type); -// break; - -// case PROJ1x2: -// case PROJ1x3: -// case PROJ1x4: -// case PROJ2x3: -// case PROJ2x4: -// case PROJ3x4: -// plotProjection(type); -// break; -// default: -// std::cout<<"GenericAxes::plotData(), Invalid type specified, cannot plot"<<std::endl; -// exit(1); -// } -// } void GenericAxes::setYLims(double ymin, double ymax){ ylims[0] = ymin; ylims[1] = ymax; @@ -88,39 +42,19 @@ void GenericAxes::getXLims(double *min, double *max){ *min = xlims[0]; *max = xlims[1]; } + void GenericAxes::setType(int t){ if (t<WAVE1 || t>PROJ3x4){ std::cout<<"Invalid Axes type specified"; return; - } - + } type = t; } + int GenericAxes::getType(){ return type; } - -// void GenericAxes::setWaveformColor(GLfloat r, GLfloat g, GLfloat b){ -// waveColor[0] = r; -// waveColor[1] = g; -// waveColor[2] = b; -// } -// void GenericAxes::setThresholdColor(GLfloat r, GLfloat g, GLfloat b){ -// thresholdColor[0] = r; -// thresholdColor[1] = g; -// thresholdColor[2] = b; -// } -// void GenericAxes::setPointColor(GLfloat r, GLfloat g, GLfloat b){ -// pointColor[0] = r; -// pointColor[1] = g; -// pointColor[2] = b; -// } -// void GenericAxes::setGridColor(GLfloat r, GLfloat g, GLfloat b){ -// gridColor[0] = r; -// gridColor[1] = g; -// gridColor[2] = b; -// } void GenericAxes::setPosition(int x, int y, double w, double h){ BaseUIElement::setPosition(x,y,w,h); resizedFlag = true; diff --git a/Source/Processors/Visualization/SpikePlotting/StereotrodePlot.cpp b/Source/Processors/Visualization/SpikePlotting/StereotrodePlot.cpp new file mode 100644 index 0000000000000000000000000000000000000000..c5fc78b0f6a6098ec226228e7f02166af609ad1b --- /dev/null +++ b/Source/Processors/Visualization/SpikePlotting/StereotrodePlot.cpp @@ -0,0 +1,297 @@ +#include "StereotrodePlot.h" +#include "../SpikeObject.h" +#include "PlotUtils.h" + +StereotrodePlot::StereotrodePlot(): + BaseUIElement(), titleHeight(0), enableTitle(true), limitsChanged(true) +{ + plotTitle = (char*) "Stereotrode Plot"; + +} + +StereotrodePlot::StereotrodePlot(int x, int y, int w, int h, char *n): + BaseUIElement(x,y,w,h,1), titleHeight(0), enableTitle(true), limitsChanged(true) +{ + plotTitle = n; + titleBox = TitleBox(x, y+h-titleHeight-3, w, titleHeight+3, plotTitle); + + initAxes(); +} + +StereotrodePlot::~StereotrodePlot(){ +} + +// Each plot needs to update its children axes when its redraw gets called. +// it also needs to call the parent plot when children axes get added it +// should place them in the correct location because it KNOWS where WAVE1 and PROJ1x3 +// should go by default. This isn't as general as it should be but its a good push in +// the right direction + +void StereotrodePlot::redraw(){ + //std::cout<<"StereotrodePlot() starting drawing"<<std::endl;\ + BaseUIElement::clearNextDraw = true; + BaseUIElement::redraw(); + + wAxes[0].redraw(); + wAxes[1].redraw(); +} + +// This would normally happen for collection of axes but an electrode plot doesn't have a collection instead its a single axes +void StereotrodePlot::processSpikeObject(SpikeObject s){ + //std::cout<<"ElectrdePlot::processSpikeObject()"<<std::endl; + wAxes[0].updateSpikeData(s); + wAxes[1].updateSpikeData(s); + //pAxesStereotrode.updateSpikeData(s); +} +void StereotrodePlot::setTitle(char *n){ + plotTitle = n; +} + +void StereotrodePlot::setEnabled(bool e){ + BaseUIElement::enabled = e; + + wAxes[0].setEnabled(e); + wAxes[1].setEnabled(e); + //pAxesStereotrode.setEnabled(e); +} + +bool StereotrodePlot::getEnabled(){ + return BaseUIElement::enabled; +} + + +void StereotrodePlot::initAxes(){ + initLimits(); + + int minX = BaseUIElement::xpos; + int minY = BaseUIElement::ypos; + + double axesWidth = BaseUIElement::width/2; + double axesHeight = (BaseUIElement::height - titleHeight); + + + wAxes[0] = WaveAxes(minX, minY, axesWidth/2, axesHeight, WAVE1); + wAxes[1] = WaveAxes(minX + axesWidth/2, minY, axesWidth/2, axesHeight, WAVE2); + //pAxesStereotrode = ProjectionAxes(minX + axesWidth, minY, axesWidth, axesHeight, PROJ1x2) + + //axes.setEnabled(false); + wAxes[0].setYLims(-1*pow(2,11), pow(2,14)*1.6); + wAxes[1].setYLims(-1*pow(2,11), pow(2,14)*1.6); + ////pAxesStereotrodeStereotrode.setYLims(-1*pow(2,11), pow(2,14)*1.6); + //pAxesStereotrode.setXLims(-1*pow(2,11), pow(2,14)*1.6); + + wAxes[0].setWaveformColor(1.0, 1.0, 1.0); + wAxes[1].setWaveformColor(1.0, 1.0, 1.0); + //pAxesStereotrode.setWaveformColor(1.0, 1.0, 1.0); + +} + +void StereotrodePlot::setPosition(int x, int y, double w, double h){ + BaseUIElement::setPosition(x,y,w,h); + int minX = BaseUIElement::xpos; + int minY = BaseUIElement::ypos; + + double axesWidth = BaseUIElement::width; + double axesHeight = BaseUIElement::height - titleHeight; + + wAxes[0] = WaveAxes(minX, minY, axesWidth/2, axesHeight, WAVE1); + wAxes[1] = WaveAxes(minX + axesWidth/2, minY, axesWidth/2, axesHeight, WAVE2); + //pAxesStereotrode = ProjectionAxes(minX + axesWidth, minY, axesWidth, axesHeight, PROJ1x2) + + titleBox.setPosition(x, y+h-titleHeight-3, w, titleHeight+3); +} + +int StereotrodePlot::getNumberOfAxes(){ + return 1;; +} + +void StereotrodePlot::clearOnNextDraw(bool b){ + BaseUIElement::clearNextDraw = b; +} + +void StereotrodePlot::setTitleEnabled(bool e){ + + // if the new setting does not equal the old than clear on the next draw + clearNextDraw = !(e!=enableTitle); + + enableTitle = e; + if (e) + titleHeight = 15; + else + titleHeight = 0; + + setPosition(BaseUIElement::xpos, BaseUIElement::ypos, + BaseUIElement::width, BaseUIElement::height); +} +void StereotrodePlot::initLimits(){ + for (int i=0; i<4; i++) + { + limits[i][0] = -1*pow(2,11); + limits[i][1] = pow(2,14); + } + +} + +void StereotrodePlot::getPreferredDimensions(double *w, double *h){ + *w = 75; + *h = 75; +} +// void StereotrodePlot::mouseDown(int x, int y){ + +// // selectedAxesN = -1; +// // std::list<GenericAxes>::iterator i; +// // int idx=-1; +// // bool hit = false; + +// // selectedAxes = NULL; +// // for (i=axesList.begin(); i!=axesList.end(); ++i) +// // { +// // if (i->hitTest(x,y)) +// // { +// // selectedAxes = addressof(*i); +// // selectedAxesN = i->getType(); +// // hit = true; +// // // break; +// // } +// // idx++; +// // } +// // if (!hit) +// // selectedAxes = NULL; +// // if (selectedAxes != NULL) +// // std::cout<<"StereotrodePlot::mouseDown() hit:"<<selectedAxes<<" AxesType:"<<selectedaxes.getType()<<std::endl; +// // else +// // std::cout<<"StereotrodePlot::mouseDown() NO HIT!"<<std::endl; + +// } +// void StereotrodePlot::mouseDragX(int dx, bool shift, bool ctrl){ + +// // if (selectedAxes == NULL || dx==0) +// // return; +// // // zoomAxes(selectedaxes.getType(), true, dx>0); +// // if (shift) +// // zoomAxes(selectedAxesN, true, dx); +// // if (ctrl) +// // panAxes(selectedAxesN, true, dx); + +// } +// void StereotrodePlot::mouseDragY(int dy, bool shift, bool ctrl){ +// if (selectedAxes == NULL || dy==0) +// return; +// if(shift) +// zoomAxes(selectedAxesN, false, dy); +// if(ctrl) +// panAxes(selectedAxesN, false, dy); +// } + +// void StereotrodePlot::zoomAxes(int n, bool xdim, int zoom){ +// // std::cout<<"StereotrodePlot::zoomAxes() n:"<< n<<" xdim"<< xdim<<" in:"<<zoomin<<std::endl; +// // If trying to zoom an invalid axes type +// if (n<WAVE1 || n>PROJ3x4) +// return; +// if (n<=WAVE4) +// zoomWaveform(n, xdim, zoom); +// else +// zoomProjection(n, xdim, zoom); +// } + +// void StereotrodePlot::zoomWaveform(int n, bool xdim, int zoom){ + +// // waveform plots don't have a xlimits +// if (xdim) +// return; +// // std::cout<<"Zooming Waveform:"<<n<<" zoomin:"<<zoomin<<" "; +// double min, max; + +// if(xdim) +// return; + +// min = limits[n][0]; +// max = limits[n][1]; + +// double mean = (max + min)/2.0f; +// double delta = max - mean; +// delta = delta / pow(.99, -1*zoom); + +// min = mean - delta; +// max = mean + delta; + +// limits[n][0] = min; +// limits[n][1] = max; + +// limitsChanged = true; +// } + +// void StereotrodePlot::panAxes(int n, bool xdim, int panval){ +// // std::cout<<"StereotrodePlot::zoomAxes() n:"<< n<<" xdim"<< xdim<<" in:"<<zoomin<<std::endl; +// // If trying to zoom an invalid axes type +// if (n<WAVE1 || n>PROJ3x4) +// return; +// if (n<=WAVE4) +// panWaveform(n, xdim, panval); +// else +// panProjection(n, xdim, panval); +// } + +// void StereotrodePlot::panWaveform(int n, bool xdim, int pan){ + +// // waveform plots don't have a xlimits +// if (xdim) +// return; +// // std::cout<<"Panning Waveform:"<<n<<" pan:"<<pan<<" "<<std::endl; +// double min, max; + +// if(xdim) +// return; + +// min = limits[n][0]; +// max = limits[n][1]; + +// double dy = max-min; + +// // Need to grab something if pan event is driven by the keyboard, which means that all the plots are getting panned so this should be okay +// if (selectedAxes == NULL) +// selectedAxes = &axesList.front(); + +// double yPixels = (BaseUIElement::height - titleHeight)/2.0; + +// double pixelWidth = -1 * dy/yPixels; + +// double delta = pan * pixelWidth; +// min = min + delta; +// max = max + delta; + +// limits[n][0] = min; +// limits[n][1] = max; + +// limitsChanged = true; +// } + + + +bool StereotrodePlot::processKeyEvent(SimpleKeyEvent k){ + // std::cout<<"Key:"<<(char)k.key<<std::endl; + // switch(k.key) + // { + // case '=': + // for (int i=0; i<=WAVE4; i++) + // zoomWaveform(i, false, 3); + // break; + // case '+': + // for (int i=0; i<=WAVE4; i++) + // panWaveform(i, false, 3); + // break; + // case '-': + // for (int i=0; i<=WAVE4; i++) + // zoomWaveform(i, false, -3); + // break; + // case '_': + // for (int i=0; i<=WAVE4; i++) + // panWaveform(i, false, -3); + // break; + // case 'C': + // clearOnNextDraw(true); + // break; + // } +} + + diff --git a/Source/Processors/Visualization/SpikePlotting/StereotrodePlot.h b/Source/Processors/Visualization/SpikePlotting/StereotrodePlot.h new file mode 100644 index 0000000000000000000000000000000000000000..2b22bc7d6d4e931d776dba1334a731f34c887de2 --- /dev/null +++ b/Source/Processors/Visualization/SpikePlotting/StereotrodePlot.h @@ -0,0 +1,81 @@ +#ifndef STEROETRODE_PLOT_H_ +#define STEROETRODE_PLOT_H_ + +#if defined(__linux__) + #include <GL/glut.h> +#else + #include <GLUT/glut.h> +#endif +#include <list> +#include <math.h> + +#include "WaveAxes.h" +#include "ProjectionAxes.h" +#include "TitleBox.h" +#include "BaseUIElement.h" +#include "TetrodeSource.h" +#include "PlotUtils.h" +#include "SimpleKeyEvent.h" + + +class StereotrodePlot : public BaseUIElement{ + + char *plotTitle; + + TitleBox titleBox; + + bool enabled; + bool enableTitle; + void drawTitle(); + + double titleHeight; + + bool limitsChanged; + double limits[1][2]; + + WaveAxes wAxes[2]; + //ProjectionAxes pAxes; + + + + // void zoomAxes(int n, bool xdim, int zoomval); + // void zoomProjection (int n, bool xdim, int zoomval); + // void zoomWaveform (int n, bool xdim, int zoomval); + + // void panAxes(int n, bool xdim, int panval); + // void panProjection (int n, bool xdim, int panval); + // void panWaveform(int n, bool xdim, int panval); + + void initLimits(); + +public: + StereotrodePlot(); + StereotrodePlot(int x, int y,int w,int h, char *n); + ~StereotrodePlot(); + + void initAxes(); + void redraw(); + void setTitle(char *n); + void setEnabled(bool enabled); + bool getEnabled(); + void setPosition(int,int,double,double); + + void getPreferredDimensions(double*, double*); + + int getNumberOfAxes(); + void clearOnNextDraw(bool c); + void setTitleEnabled(bool e); + + void mouseDown(int x, int y); + + void mouseDragX(int dx, bool shift, bool ctr); + void mouseDragY(int dy, bool shift, bool ctr); + + bool processKeyEvent(SimpleKeyEvent k); + + void processSpikeObject(SpikeObject s); +}; + + + +#endif diff --git a/Source/Processors/Visualization/SpikePlotting/WaveAxes.cpp b/Source/Processors/Visualization/SpikePlotting/WaveAxes.cpp index c38fd955bd6fcca46905fd62e94916c5a44b306f..90e50883bbda84eac5b1900611e8b9ddb69f9bf2 100644 --- a/Source/Processors/Visualization/SpikePlotting/WaveAxes.cpp +++ b/Source/Processors/Visualization/SpikePlotting/WaveAxes.cpp @@ -39,7 +39,7 @@ WaveAxes::WaveAxes(int x, int y, double w, double h, int t): } void WaveAxes::updateSpikeData(SpikeObject newSpike){ - std::cout<<"WaveAxes::updateSpikeData()"<<std::endl; + //std::cout<<"WaveAxes::updateSpikeData()"<<std::endl; GenericAxes::updateSpikeData(newSpike); } @@ -75,12 +75,15 @@ void WaveAxes::plot(){ //compute the spatial width for each wawveform sample float dx = 1; float x = 0; - int sampIdx = 0; + + // type corresponds to channel so we need to calculate the starting + // sample based upon which channel is getting plotted + // type values are defined in PlotUtils.h + int sampIdx = s.nSamples * type; // + std::cout<<"Starting with idx:"<<sampIdx<<std::endl; //Draw the individual waveform points connected with a line - // if drawWaveformPoints is set to false then force the drawing of the line, _SOMETHING_ must be drawn glColor3fv(waveColor); - glLineWidth(1); glBegin( GL_LINE_STRIP ); diff --git a/open-ephys.jucer b/open-ephys.jucer index 1797c8186c9c26254ea530610c172aeac4355e71..5b60f8d2a5e1886d020b18442d04a0cb300bfa94 100644 --- a/open-ephys.jucer +++ b/open-ephys.jucer @@ -13,7 +13,7 @@ juceFolder="JuceLibraryCode" extraLinkerFlags="-lftdi -lftgl" objCExtraSuffix="fea2mT"/> <LINUX_MAKE targetFolder="Builds/Linux" vstFolder="~/SDKs/vstsdk2.4" juceFolder="JuceLibraryCode" - extraLinkerFlags="-lftdi -lftgl" extraCompilerFlags="-export-dynamic -g"/> + extraLinkerFlags="-lftdi -lftgl" extraCompilerFlags="-export-dynamic"/> </EXPORTFORMATS> <CONFIGURATIONS> <CONFIGURATION name="Debug" isDebug="1" optimisation="1" targetName="open-ephys" @@ -156,6 +156,10 @@ </GROUP> <GROUP id="W4eqkOy" name="Visualization"> <GROUP id="g8GOfh" name="SpikePlotting"> + <FILE id="PzmX0I" name="StereotrodePlot.cpp" compile="1" resource="0" + file="Source/Processors/Visualization/SpikePlotting/StereotrodePlot.cpp"/> + <FILE id="LPK6G1" name="StereotrodePlot.h" compile="0" resource="0" + file="Source/Processors/Visualization/SpikePlotting/StereotrodePlot.h"/> <FILE id="EgoljI" name="ElectrodePlot.cpp" compile="1" resource="0" file="Source/Processors/Visualization/SpikePlotting/ElectrodePlot.cpp"/> <FILE id="oFUMq0" name="ElectrodePlot.h" compile="0" resource="0" file="Source/Processors/Visualization/SpikePlotting/ElectrodePlot.h"/>