diff --git a/DeviceAdapters/TeledyneDalsaGigE/GigENano.vcxproj b/DeviceAdapters/TeledyneDalsaGigE/GigENano.vcxproj
new file mode 100644
index 0000000000..ad03281691
--- /dev/null
+++ b/DeviceAdapters/TeledyneDalsaGigE/GigENano.vcxproj
@@ -0,0 +1,171 @@
+
+
+
+
+ Debug
+ Win32
+
+
+ Debug
+ x64
+
+
+ Release
+ Win32
+
+
+ Release
+ x64
+
+
+
+ {DE209272-1DA7-4551-9D34-3ECE99DDE827}
+ Win32Proj
+ GigENano
+ 10.0
+
+
+
+ DynamicLibrary
+ true
+ Unicode
+ v142
+
+
+ DynamicLibrary
+ true
+ Unicode
+ v142
+
+
+ DynamicLibrary
+ false
+ true
+ Unicode
+ v142
+
+
+ DynamicLibrary
+ false
+ true
+ Unicode
+ v142
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ true
+
+
+ true
+
+
+ false
+
+
+ false
+
+
+
+
+
+ Level3
+ Disabled
+ WIN32;_DEBUG;_WINDOWS;_USRDLL;GIGENANO_EXPORTS;%(PreprocessorDefinitions)
+ $(SAPERADIR)\Include;$(SAPERADIR)\Classes\Basic;%(AdditionalIncludeDirectories)
+
+
+ Windows
+ true
+
+
+
+
+
+
+ Level3
+ Disabled
+ WIN32;_DEBUG;_WINDOWS;_USRDLL;GIGENANO_EXPORTS;%(PreprocessorDefinitions)
+ $(SAPERADIR)\Include;$(SAPERADIR)\Classes\Basic;%(AdditionalIncludeDirectories)
+
+
+ Windows
+ true
+
+
+
+
+ Level3
+
+
+ MaxSpeed
+ true
+ true
+ WIN32;NDEBUG;_WINDOWS;_USRDLL;GIGENANO_EXPORTS;%(PreprocessorDefinitions)
+ $(SAPERADIR)\Include;$(SAPERADIR)\Classes\Basic;%(AdditionalIncludeDirectories)
+
+
+ Windows
+ true
+ true
+ true
+
+
+
+
+ Level3
+
+
+ MaxSpeed
+ true
+ true
+ WIN32;NDEBUG;_WINDOWS;_USRDLL;GIGENANO_EXPORTS;%(PreprocessorDefinitions)
+ $(SAPERADIR)\Include;$(SAPERADIR)\Classes\Basic;%(AdditionalIncludeDirectories)
+
+
+ Windows
+ true
+ true
+ true
+
+
+
+
+
+
+
+
+
+
+
+
+
+ {b8c95f39-54bf-40a9-807b-598df2821d55}
+
+
+
+
+
+
\ No newline at end of file
diff --git a/DeviceAdapters/TeledyneDalsaGigE/GigENano.vcxproj.filters b/DeviceAdapters/TeledyneDalsaGigE/GigENano.vcxproj.filters
new file mode 100644
index 0000000000..c65818c50e
--- /dev/null
+++ b/DeviceAdapters/TeledyneDalsaGigE/GigENano.vcxproj.filters
@@ -0,0 +1,30 @@
+
+
+
+
+ {4FC737F1-C7A5-4376-A066-2A32D752A2FF}
+ cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx
+
+
+ {93995380-89BD-4b04-88EB-625FBE52EBFB}
+ h;hpp;hxx;hm;inl;inc;xsd
+
+
+ {67DA6AB6-F800-4c08-8B7A-83BB121AAD01}
+ rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms
+
+
+
+
+ Header Files
+
+
+
+
+ Source Files
+
+
+
+
+
+
\ No newline at end of file
diff --git a/DeviceAdapters/TeledyneDalsaGigE/TestCamera.cpp b/DeviceAdapters/TeledyneDalsaGigE/TestCamera.cpp
new file mode 100644
index 0000000000..a8282e4fec
--- /dev/null
+++ b/DeviceAdapters/TeledyneDalsaGigE/TestCamera.cpp
@@ -0,0 +1,859 @@
+/////////////////////////////////////////////////////////
+// FILE: TestCamera.cpp
+// PROJECT: Teledyne DALSA Micro-Manager Glue Library
+//-------------------------------------------------------
+// AUTHOR: Robert Frazee, rfraze1@lsu.edu
+
+#include "TestCamera.h"
+#include "../MMDevice/ModuleInterface.h"
+#include "stdio.h"
+#include "conio.h"
+#include "math.h"
+#include "sapclassbasic.h"
+#include
+
+using namespace std;
+
+const char* g_CameraName = "GigE Nano";
+const char* g_PixelType_8bit = "8bit";
+const char* g_PixelType_10bit = "10bit";
+const char* g_PixelType_12bit = "12bit";
+
+const char* g_CameraModelProperty = "Model";
+const char* g_CameraModel_A = "Nano-M1930-NIR";
+
+// g_CameraAcqDeviceNumberProperty
+// g_CameraServerNameProperty
+// g_CameraConfigFilenameProperty
+const char* g_CameraAcqDeviceNumberProperty = "Acquisition Device Number";
+const char* g_CameraAcqDeviceNumber_Def = "0";
+const char* g_CameraServerNameProperty = "Server Name";
+const char* g_CameraServerName_Def = "Nano-M1930-NIR_1";
+const char* g_CameraConfigFilenameProperty = "Config Filename";
+const char* g_CameraConfigFilename_Def = "NoFile";
+
+
+///////////////////////////////////////////////////////////////////////////////
+// Exported MMDevice API
+///////////////////////////////////////////////////////////////////////////////
+
+/**
+ * List all supported hardware devices here
+ */
+MODULE_API void InitializeModuleData()
+{
+ RegisterDevice(g_CameraName, MM::CameraDevice, "GigE Nano Camera Device");
+}
+
+MODULE_API MM::Device* CreateDevice(const char* deviceName)
+{
+ if (deviceName == 0)
+ return 0;
+
+ // decide which device class to create based on the deviceName parameter
+ if (strcmp(deviceName, g_CameraName) == 0)
+ {
+ // create camera
+ return new TestCamera();
+ }
+
+ // ...supplied name not recognized
+ // to heck with it, return a device anyway
+ return new TestCamera();
+}
+
+MODULE_API void DeleteDevice(MM::Device* pDevice)
+{
+ delete pDevice;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+// TestCamera implementation
+// ~~~~~~~~~~~~~~~~~~~~~~~
+
+/**
+* TestCamera constructor.
+* Setup default all variables and create device properties required to exist
+* before intialization. In this case, no such properties were required. All
+* properties will be created in the Initialize() method.
+*
+* As a general guideline Micro-Manager devices do not access hardware in the
+* the constructor. We should do as little as possible in the constructor and
+* perform most of the initialization in the Initialize() method.
+*/
+TestCamera::TestCamera() :
+ binning_ (1),
+ gain_(1),
+ bytesPerPixel_(1),
+ bitsPerPixel_(8),
+ initialized_(false),
+ roiX_(0),
+ roiY_(0),
+ thd_(0),
+ sequenceRunning_(false),
+ SapFormatBytes_(1)
+{
+ // call the base class method to set-up default error codes/messages
+ InitializeDefaultErrorMessages();
+
+ // Description property
+ int ret = CreateProperty(MM::g_Keyword_Description, "GigE Nano Camera Adapter", MM::String, true);
+ assert(ret == DEVICE_OK);
+
+ // camera type pre-initialization property
+ ret = CreateProperty(g_CameraModelProperty, g_CameraModel_A, MM::String, false, 0, true);
+ assert(ret == DEVICE_OK);
+
+ vector modelValues;
+ modelValues.push_back(g_CameraModel_A);
+ modelValues.push_back(g_CameraModel_A);
+
+ ret = SetAllowedValues(g_CameraModelProperty, modelValues);
+ assert(ret == DEVICE_OK);
+
+ // Sapera++ library stuff
+
+ int serverCount = SapManager::GetServerCount();
+ if(serverCount == 0)
+ {
+ ErrorBox((LPCWSTR)L"Initialization Error", (LPCWSTR)L"No servers!");
+ }
+
+ acqServerName_ = new char[CORSERVER_MAX_STRLEN];
+ configFilename_ = new char[MAX_PATH];
+
+ ret = CreateProperty(g_CameraAcqDeviceNumberProperty, g_CameraAcqDeviceNumber_Def, MM::Integer, false, 0, true);
+ assert(ret == DEVICE_OK);
+
+ ret = CreateProperty(g_CameraServerNameProperty, g_CameraServerName_Def, MM::String, false, 0, true);
+ assert(ret == DEVICE_OK);
+
+ ret = CreateProperty(g_CameraConfigFilenameProperty, g_CameraConfigFilename_Def, MM::String, false, 0, true);
+ assert(ret == DEVICE_OK);
+
+ // create live video thread
+ thd_ = new SequenceThread(this);
+}
+
+/**
+* TestCamera destructor.
+* If this device used as intended within the Micro-Manager system,
+* Shutdown() will be always called before the destructor. But in any case
+* we need to make sure that all resources are properly released even if
+* Shutdown() was not called.
+*/
+TestCamera::~TestCamera()
+{
+ if (initialized_)
+ Shutdown();
+}
+
+/**
+* Obtains device name.
+* Required by the MM::Device API.
+*/
+void TestCamera::GetName(char* name) const
+{
+ // We just return the name we use for referring to this
+ // device adapter.
+ CDeviceUtils::CopyLimitedString(name, g_CameraName);
+}
+
+/**
+* Intializes the hardware.
+* Typically we access and initialize hardware at this point.
+* Device properties are typically created here as well.
+* Required by the MM::Device API.
+*/
+int TestCamera::Initialize()
+{
+ if (initialized_)
+ return DEVICE_OK;
+
+ //SapManager::DisplayMessage("This plugin logs debug messages. Press no so they don't all pop up like this.");
+ // set property list
+ // -----------------
+
+ // binning
+ CPropertyAction *pAct = new CPropertyAction (this, &TestCamera::OnBinning);
+ //@TODO: Check what the actual binning value is and set that
+ // For now, set binning to 1 for MM and set that on the camera later
+ int ret = CreateProperty(MM::g_Keyword_Binning, "1", MM::Integer, false, pAct);
+ assert(ret == DEVICE_OK);
+
+ vector binningValues;
+ binningValues.push_back("1");
+ binningValues.push_back("2");
+ binningValues.push_back("4");
+
+ ret = SetAllowedValues(MM::g_Keyword_Binning, binningValues);
+ assert(ret == DEVICE_OK);
+
+ //Sapera stuff
+ // g_CameraAcqDeviceNumberProperty
+ // g_CameraServerNameProperty
+ // g_CameraConfigFilenameProperty
+ long tmpDeviceNumber;
+ if(GetProperty(g_CameraAcqDeviceNumberProperty, tmpDeviceNumber) != DEVICE_OK)
+ {
+ //SapManager::DisplayMessage("Failed to retrieve AcqDeviceNumberProperty");
+ return DEVICE_ERR;
+ }
+ acqDeviceNumber_ = (UINT32)tmpDeviceNumber;
+
+ if(false)//GetProperty(g_CameraServerNameProperty, acqServerName_) != DEVICE_OK)
+ {
+ //SapManager::DisplayMessage("Failed to retrieve ServerNameProperty");
+ return DEVICE_ERR;
+ }
+ acqServerName_ = (char *)g_CameraServerName_Def;
+
+ if(false)//GetProperty(g_CameraConfigFilenameProperty, configFilename_) != DEVICE_OK)
+ {
+ //SapManager::DisplayMessage("Failed to retrieve ConfigFilenameProperty");
+ return DEVICE_ERR;
+ }
+ configFilename_ = "NoFile";
+
+ //SapManager::DisplayMessage("(Sapera app)Creating loc_ object");
+ SapLocation loc_(acqServerName_, acqDeviceNumber_);
+ //SapManager::DisplayMessage("(Sapera app)Created loc_ object");
+ //SapManager::DisplayMessage("(Sapera app)GetResourceCount for ResourceAcqDevice starting");
+ if(SapManager::GetResourceCount(acqServerName_, SapManager::ResourceAcqDevice) > 0)
+ {
+ //SapManager::DisplayMessage("(Sapera app)GetResourceCount for ResourceAcqDevice found something");
+ if(strcmp(configFilename_, "NoFile") == 0)
+ AcqDevice_ = SapAcqDevice(loc_, false);
+ else
+ AcqDevice_ = SapAcqDevice(loc_, configFilename_);
+
+ Buffers_ = SapBufferWithTrash(2, &AcqDevice_);
+ AcqDeviceToBuf_ = SapAcqDeviceToBuf(&AcqDevice_, &Buffers_);
+ Xfer_ = &AcqDeviceToBuf_;
+
+ if(!AcqDevice_.Create())
+ {
+ ret = FreeHandles();
+ if (ret != DEVICE_OK)
+ {
+ //SapManager::DisplayMessage("Failed to FreeHandles during Acq_.Create() for ResourceAcqDevice");
+ return ret;
+ }
+ //SapManager::DisplayMessage("Failed to create Acq_ for ResourceAcqDevice");
+ return DEVICE_INVALID_INPUT_PARAM;
+ }
+ }
+ //SapManager::DisplayMessage("(Sapera app)GetResourceCount for ResourceAcqDevice done");
+ //SapManager::DisplayMessage("(Sapera app)Creating Buffers_");
+ if(!Buffers_.Create())
+ {
+ ret = FreeHandles();
+ if (ret != DEVICE_OK)
+ return ret;
+ return DEVICE_NATIVE_MODULE_FAILED;
+ }
+ //SapManager::DisplayMessage("(Sapera app)Creating Xfer_");
+ if(Xfer_ && !Xfer_->Create())
+ {
+ //SapManager::DisplayMessage("Xfer_ creation failed");
+ ret = FreeHandles();
+ if (ret != DEVICE_OK)
+ return ret;
+ return DEVICE_NATIVE_MODULE_FAILED;
+ }
+ //SapManager::DisplayMessage("(Sapera app)Starting Xfer");
+ //Start continuous grab
+ //Xfer_->Grab();
+ //SapManager::DisplayMessage("(Sapera app)Sapera Initialization for TestCamera complete");
+
+ if(!AcqDevice_.GetFeatureValue("ExposureTime", &exposureMs_))
+ return DEVICE_ERR;
+ exposureMs_ = exposureMs_ / 1000;
+
+ // synchronize bit depth with camera
+
+ char acqFormat[10];
+ AcqDevice_.GetFeatureValue("PixelFormat", acqFormat, 10);
+ if(strcmp(acqFormat, "Mono8") == 0)
+ {
+ // Setup Micro-Manager for 8bit pixels
+ SapFormatBytes_ = 1;
+ bitsPerPixel_ = 8;
+ bytesPerPixel_ = 1;
+ //resize the SapBuffer
+ int ret = SapBufferReformat(SapFormatMono8, "Mono8");
+ if(ret != DEVICE_OK)
+ {
+ return ret;
+ }
+ ResizeImageBuffer();
+ pAct = new CPropertyAction (this, &TestCamera::OnPixelType);
+ ret = CreateProperty(MM::g_Keyword_PixelType, g_PixelType_8bit, MM::String, false, pAct);
+ assert(ret == DEVICE_OK);
+ }
+ if(strcmp(acqFormat, "Mono10") == 0)
+ {
+ // Setup Micro-Manager for 8bit pixels
+ SapFormatBytes_ = 2;
+ bitsPerPixel_ = 10;
+ bytesPerPixel_ = 2;
+ //resize the SapBuffer
+ int ret = SapBufferReformat(SapFormatMono10, "Mono10");
+ if(ret != DEVICE_OK)
+ {
+ return ret;
+ }
+ ResizeImageBuffer();
+ pAct = new CPropertyAction (this, &TestCamera::OnPixelType);
+ ret = CreateProperty(MM::g_Keyword_PixelType, g_PixelType_10bit, MM::String, false, pAct);
+ assert(ret == DEVICE_OK);
+ }
+
+
+ // pixel type
+
+
+ vector pixelTypeValues;
+ pixelTypeValues.push_back(g_PixelType_8bit);
+ pixelTypeValues.push_back(g_PixelType_10bit);
+
+
+ ret = SetAllowedValues(MM::g_Keyword_PixelType, pixelTypeValues);
+ assert(ret == DEVICE_OK);
+
+ // Set Binning to 1
+ if(!AcqDevice_.SetFeatureValue("BinningVertical", 1))
+ return DEVICE_ERR;
+ if(!AcqDevice_.SetFeatureValue("BinningHorizontal", 1))
+ return DEVICE_ERR;
+
+
+ // Setup gain
+ pAct = new CPropertyAction(this, &TestCamera::OnGain);
+ ret = CreateProperty(MM::g_Keyword_Gain, "1.0", MM::Float, false, pAct);
+ assert(ret == DEVICE_OK);
+ if(!AcqDevice_.SetFeatureValue("Gain", 1.0))
+ return DEVICE_ERR;
+ SapFeature SapGain_(loc_);
+ if(!SapGain_.Create())
+ return DEVICE_ERR;
+ AcqDevice_.GetFeatureInfo("Gain", &SapGain_);
+ double g_low = 0.0;
+ double g_high = 0.0;
+ SapGain_.GetMax(&g_high);
+ SapGain_.GetMin(&g_low);
+ SetPropertyLimits(MM::g_Keyword_Gain, g_low, g_high);
+
+
+
+ // synchronize all properties
+ // --------------------------
+ ret = UpdateStatus();
+ if (ret != DEVICE_OK)
+ return ret;
+
+ // setup the buffer
+ // ----------------
+ ret = ResizeImageBuffer();
+ if (ret != DEVICE_OK)
+ return ret;
+
+ initialized_ = true;
+ return DEVICE_OK;
+}
+
+/**
+* Shuts down (unloads) the device.
+* Ideally this method will completely unload the device and release all resources.
+* Shutdown() may be called multiple times in a row.
+* Required by the MM::Device API.
+*/
+int TestCamera::Shutdown()
+{
+ if(!initialized_)
+ return DEVICE_OK;
+ initialized_ = false;
+ Xfer_->Freeze();
+ if(!Xfer_->Wait(5000))
+ return DEVICE_NATIVE_MODULE_FAILED;
+ int ret;
+ ret = FreeHandles();
+ if(ret != DEVICE_OK)
+ return ret;
+ return DEVICE_OK;
+}
+
+/**
+* Frees Sapera buffers and such
+*/
+int TestCamera::FreeHandles()
+{
+ if(Xfer_ && *Xfer_ && !Xfer_->Destroy()) return DEVICE_ERR;
+ if(!Buffers_.Destroy()) return DEVICE_ERR;
+ if(!Acq_.Destroy()) return DEVICE_ERR;
+ if(!AcqDevice_.Destroy()) return DEVICE_ERR;
+ return DEVICE_OK;
+}
+
+int TestCamera::ErrorBox(LPCWSTR text, LPCWSTR caption)
+{
+ return MessageBox(NULL, caption, text, (MB_ICONERROR | MB_OK));
+}
+
+/**
+* Performs exposure and grabs a single image.
+* This function blocks during the actual exposure and returns immediately afterwards
+* Required by the MM::Camera API.
+*/
+int TestCamera::SnapImage()
+{
+ // This will always be false, as no sequences will ever run
+ if(sequenceRunning_)
+ return DEVICE_CAMERA_BUSY_ACQUIRING;
+ // Start image capture
+ if(!Xfer_->Snap(1))
+ {
+ return DEVICE_ERR;
+ }
+ // Wait for either the capture to finish or 2.5 seconds, whichever is first
+ if(!Xfer_->Wait(2500))
+ {
+ return DEVICE_ERR;
+ }
+ return DEVICE_OK;
+}
+
+/**
+* Returns pixel data.
+* Required by the MM::Camera API.
+* The calling program will assume the size of the buffer based on the values
+* obtained from GetImageBufferSize(), which in turn should be consistent with
+* values returned by GetImageWidth(), GetImageHight() and GetImageBytesPerPixel().
+* The calling program allso assumes that camera never changes the size of
+* the pixel buffer on its own. In other words, the buffer can change only if
+* appropriate properties are set (such as binning, pixel type, etc.)
+*/
+const unsigned char* TestCamera::GetImageBuffer()
+{
+ // Put Sapera buffer into Micro-Manager Buffer
+ Buffers_.ReadRect(roiX_, roiY_, img_.Width(), img_.Height(), const_cast(img_.GetPixels()));
+ // Return location of the Micro-Manager Buffer
+ return const_cast(img_.GetPixels());
+}
+
+/**
+* Returns image buffer X-size in pixels.
+* Required by the MM::Camera API.
+*/
+unsigned TestCamera::GetImageWidth() const
+{
+ return img_.Width();
+}
+
+/**
+* Returns image buffer Y-size in pixels.
+* Required by the MM::Camera API.
+*/
+unsigned TestCamera::GetImageHeight() const
+{
+ return img_.Height();
+}
+
+/**
+* Returns image buffer pixel depth in bytes.
+* Required by the MM::Camera API.
+*/
+unsigned TestCamera::GetImageBytesPerPixel() const
+{
+ return img_.Depth();
+}
+
+/**
+* Returns the bit depth (dynamic range) of the pixel.
+* This does not affect the buffer size, it just gives the client application
+* a guideline on how to interpret pixel values.
+* Required by the MM::Camera API.
+*/
+unsigned TestCamera::GetBitDepth() const
+{
+ return bitsPerPixel_;
+}
+
+/**
+* Returns the size in bytes of the image buffer.
+* Required by the MM::Camera API.
+*/
+long TestCamera::GetImageBufferSize() const
+{
+ return img_.Width() * img_.Height() * GetImageBytesPerPixel();
+}
+
+/**
+* Sets the camera Region Of Interest.
+* Required by the MM::Camera API.
+* This command will change the dimensions of the image.
+* Depending on the hardware capabilities the camera may not be able to configure the
+* exact dimensions requested - but should try do as close as possible.
+* If the hardware does not have this capability the software should simulate the ROI by
+* appropriately cropping each frame.
+* This demo implementation ignores the position coordinates and just crops the buffer.
+* @param x - top-left corner coordinate
+* @param y - top-left corner coordinate
+* @param xSize - width
+* @param ySize - height
+*/
+int TestCamera::SetROI(unsigned x, unsigned y, unsigned xSize, unsigned ySize)
+{
+ if (xSize == 0 && ySize == 0)
+ {
+ // effectively clear ROI
+ ResizeImageBuffer();
+ roiX_ = 0;
+ roiY_ = 0;
+ }
+ else
+ {
+ // apply ROI
+ img_.Resize(xSize, ySize);
+ roiX_ = x;
+ roiY_ = y;
+ }
+ return DEVICE_OK;
+}
+
+/**
+* Returns the actual dimensions of the current ROI.
+* Required by the MM::Camera API.
+*/
+int TestCamera::GetROI(unsigned& x, unsigned& y, unsigned& xSize, unsigned& ySize)
+{
+ x = roiX_;
+ y = roiY_;
+
+ xSize = img_.Width();
+ ySize = img_.Height();
+
+ return DEVICE_OK;
+}
+
+/**
+* Resets the Region of Interest to full frame.
+* Required by the MM::Camera API.
+*/
+int TestCamera::ClearROI()
+{
+ ResizeImageBuffer();
+ roiX_ = 0;
+ roiY_ = 0;
+
+ return DEVICE_OK;
+}
+
+/**
+* Returns the current exposure setting in milliseconds.
+* Required by the MM::Camera API.
+*/
+double TestCamera::GetExposure() const
+{
+ return exposureMs_;
+}
+
+/**
+* Sets exposure in milliseconds.
+* Required by the MM::Camera API.
+*/
+void TestCamera::SetExposure(double exp)
+{
+ exposureMs_ = exp;
+ // Micromanager deals with exposure time in ms
+ // Sapera deals with exposure time in us
+ // As such, we convert between the two
+ AcqDevice_.SetFeatureValue("ExposureTime", (exposureMs_ * 1000));
+}
+
+/**
+* Returns the current binning factor.
+* Required by the MM::Camera API.
+*/
+int TestCamera::GetBinning() const
+{
+ return binning_;
+}
+
+/**
+* Sets binning factor.
+* Required by the MM::Camera API.
+*/
+int TestCamera::SetBinning(int binF)
+{
+ return SetProperty(MM::g_Keyword_Binning, CDeviceUtils::ConvertToString(binF));
+}
+
+int TestCamera::PrepareSequenceAcqusition()
+{
+ return DEVICE_ERR;
+}
+
+
+/**
+ * Required by the MM::Camera API
+ * Please implement this yourself and do not rely on the base class implementation
+ * The Base class implementation is deprecated and will be removed shortly
+ */
+int TestCamera::StartSequenceAcquisition(double interval_ms)
+{
+ //@TODO: Implement Sequence Acquisition
+ return DEVICE_ERR;
+ //int ret = StartSequenceAcquisition((long)(interval_ms/exposureMs_), interval_ms, true);
+ //return ret;
+}
+
+/**
+* Stop and wait for the Sequence thread finished
+*/
+int TestCamera::StopSequenceAcquisition()
+{
+ //@TODO: Implement Sequence Acquisition
+ return DEVICE_ERR;
+ /*thd_->Stop();
+ thd_->wait();
+ sequenceRunning_ = false;
+ return DEVICE_OK;*/
+}
+
+/**
+* Simple implementation of Sequence Acquisition
+* A sequence acquisition should run on its own thread and transport new images
+* coming of the camera into the MMCore circular buffer.
+*/
+int TestCamera::StartSequenceAcquisition(long numImages, double interval_ms, bool stopOnOverflow)
+{
+ //@TODO: Implement Sequence Acquisition
+ return DEVICE_ERR;
+ /*if (sequenceRunning_)
+ {
+ return DEVICE_CAMERA_BUSY_ACQUIRING;
+ }
+ int ret = GetCoreCallback()->PrepareForAcq(this);
+ if (ret != DEVICE_OK)
+ {
+ return ret;
+ }
+ sequenceRunning_ = true;
+ thd_->SetLength(10);
+ thd_->Start();
+ return DEVICE_OK; */
+}
+
+/*
+ * Inserts Image and MetaData into MMCore circular Buffer
+ */
+int TestCamera::InsertImage()
+{
+ //@TODO: Implement Sequence Acquisition
+ return GetCoreCallback()->InsertImage(this, const_cast(img_.GetPixels()), GetImageWidth(), GetImageHeight(), GetImageBytesPerPixel());
+}
+
+
+bool TestCamera::IsCapturing() {
+ //@TODO: Implement Sequence Acquisition
+ return sequenceRunning_;
+}
+
+
+///////////////////////////////////////////////////////////////////////////////
+// TestCamera Action handlers
+///////////////////////////////////////////////////////////////////////////////
+
+/**
+* Handles "Binning" property.
+*/
+int TestCamera::OnBinning(MM::PropertyBase* pProp, MM::ActionType eAct)
+{
+ if (eAct == MM::AfterSet)
+ {
+ long binSize;
+ pProp->Get(binSize);
+ binning_ = (int)binSize;
+ if(!AcqDevice_.SetFeatureValue("BinningVertical", binning_))
+ return DEVICE_ERR;
+ if(!AcqDevice_.SetFeatureValue("BinningHorizontal", binning_))
+ return DEVICE_ERR;
+ return ResizeImageBuffer();
+ }
+ else if (eAct == MM::BeforeGet)
+ {
+ pProp->Set((long)binning_);
+ }
+
+ return DEVICE_OK;
+}
+
+/**
+* Handles "PixelType" property.
+*/
+int TestCamera::OnPixelType(MM::PropertyBase* pProp, MM::ActionType eAct)
+{
+ //bytesPerPixel_ = 1;
+ //ResizeImageBuffer();
+ //return DEVICE_OK;
+ if (eAct == MM::AfterSet)
+ {
+ //SapManager::DisplayMessage("(Sapera app)OnPixelType MM:AfterSet");
+ string val;
+ pProp->Get(val);
+ if (val.compare(g_PixelType_8bit) == 0)
+ {
+ if(SapFormatBytes_ != 1)
+ {
+ SapFormatBytes_ = 1;
+ bitsPerPixel_ = 8;
+ //resize the SapBuffer
+ int ret = SapBufferReformat(SapFormatMono8, "Mono8");
+ if(ret != DEVICE_OK)
+ {
+ return ret;
+ }
+ }
+ bytesPerPixel_ = 1;
+ }
+ else if (val.compare(g_PixelType_10bit) == 0)
+ {
+ if(SapFormatBytes_ != 2)
+ {
+ SapFormatBytes_ = 2;
+ bitsPerPixel_ = 10;
+ //resize the SapBuffer
+ int ret = SapBufferReformat(SapFormatMono16, "Mono10");
+ if(ret != DEVICE_OK)
+ {
+ return ret;
+ }
+ }
+ bytesPerPixel_ = 2;
+ }
+ else
+ assert(false);
+
+ ResizeImageBuffer();
+ }
+ else if (eAct == MM::BeforeGet)
+ {
+ if (bytesPerPixel_ == 1)
+ pProp->Set(g_PixelType_8bit);
+ else if (bytesPerPixel_ == 2)
+ pProp->Set(g_PixelType_10bit);
+ else
+ assert(false); // this should never happen
+ }
+
+ return DEVICE_OK;
+}
+
+/**
+* Handles "Gain" property.
+*/
+int TestCamera::OnGain(MM::PropertyBase* pProp, MM::ActionType eAct)
+{
+ if (eAct == MM::AfterSet)
+ {
+ //SapManager::DisplayMessage("(Sapera app)OnGain MM:AfterSet");
+ pProp->Get(gain_);
+ AcqDevice_.SetFeatureValue("Gain", gain_);
+ }
+ else if (eAct == MM::BeforeGet)
+ {
+ pProp->Set(gain_);
+ }
+
+ return DEVICE_OK;
+}
+
+
+///////////////////////////////////////////////////////////////////////////////
+// Private TestCamera methods
+///////////////////////////////////////////////////////////////////////////////
+
+/**
+* Sync internal image buffer size to the chosen property values.
+*/
+int TestCamera::ResizeImageBuffer()
+{
+ img_.Resize(IMAGE_WIDTH/binning_, IMAGE_HEIGHT/binning_, bytesPerPixel_);
+
+ return DEVICE_OK;
+}
+
+/**
+ * Generate an image with fixed value for all pixels
+ */
+void TestCamera::GenerateImage()
+{
+ const int maxValue = (1 << MAX_BIT_DEPTH) - 1; // max for the 12 bit camera
+ const double maxExp = 1000;
+ double step = maxValue/maxExp;
+ unsigned char* pBuf = const_cast(img_.GetPixels());
+ memset(pBuf, (int) (step * max(exposureMs_, maxExp)), img_.Height()*img_.Width()*img_.Depth());
+}
+
+/*
+ * Reformat Sapera Buffer Object
+ */
+int TestCamera::SapBufferReformat(SapFormat format, const char * acqFormat)
+{
+ Xfer_->Destroy();
+ AcqDevice_.SetFeatureValue("PixelFormat", acqFormat);
+ Buffers_.Destroy();
+ Buffers_ = SapBufferWithTrash(2, &AcqDevice_);
+ Buffers_.SetFormat(format);
+ AcqDeviceToBuf_ = SapAcqDeviceToBuf(&AcqDevice_, &Buffers_);
+ Xfer_ = &AcqDeviceToBuf_;
+ if(!Buffers_.Create())
+ {
+ //SapManager::DisplayMessage("Failed to recreate Buffer - SapBufferReformat");
+ int ret = FreeHandles();
+ if (ret != DEVICE_OK)
+ return ret;
+ return DEVICE_NATIVE_MODULE_FAILED;
+ }
+ if(Xfer_ && !Xfer_->Create())
+ {
+ //SapManager::DisplayMessage("Xfer_ recreation failed - SapBufferReformat");
+ int ret = FreeHandles();
+ if (ret != DEVICE_OK)
+ return ret;
+ return DEVICE_NATIVE_MODULE_FAILED;
+ }
+ return DEVICE_OK;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+// Threading methods
+///////////////////////////////////////////////////////////////////////////////
+
+int SequenceThread::svc()
+{
+ //SapManager::DisplayMessage("SequenceThread Start");
+ long count(0);
+ while (!stop_ )//&& count < numImages_)
+ {
+ /*int ret = camera_->SnapImage();
+ if (ret != DEVICE_OK)
+ {
+ //SapManager::DisplayMessage("SequenceThread Snap failed");
+ camera_->StopSequenceAcquisition();
+ return 1;
+ }*/
+
+ int ret = camera_->InsertImage();
+ if (ret != DEVICE_OK)
+ {
+ //SapManager::DisplayMessage("SequenceThread InsertFailed");
+ camera_->StopSequenceAcquisition();
+ return 1;
+ }
+ //count++;
+ }
+ //SapManager::DisplayMessage("SequenceThread End");
+ return 0;
+}
\ No newline at end of file
diff --git a/DeviceAdapters/TeledyneDalsaGigE/TestCamera.h b/DeviceAdapters/TeledyneDalsaGigE/TestCamera.h
new file mode 100644
index 0000000000..b3808676e6
--- /dev/null
+++ b/DeviceAdapters/TeledyneDalsaGigE/TestCamera.h
@@ -0,0 +1,154 @@
+///////////////////////////////////////////////////////////////////////////////
+// FILE: TestCamera.h
+// PROJECT: Micro-Manager
+// SUBSYSTEM: DeviceAdapters
+//-----------------------------------------------------------------------------
+// DESCRIPTION: Skeleton code for the micro-manager camera adapter. Use it as
+// starting point for writing custom device adapters
+//
+// AUTHOR: Nenad Amodaj, http://nenad.amodaj.com
+//
+// COPYRIGHT: University of California, San Francisco, 2011
+//
+// LICENSE: This file is distributed under the BSD license.
+// License text is included with the source distribution.
+//
+// This file is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty
+// of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
+//
+// IN NO EVENT SHALL THE COPYRIGHT OWNER OR
+// CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+// INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES.
+//
+
+#ifndef _TestCamera_H_
+#define _TestCamera_H_
+
+#include "DeviceBase.h"
+#include "ImgBuffer.h"
+#include "DeviceThreads.h"
+#include "ImgBuffer.h"
+#include "stdio.h"
+#include "conio.h"
+#include "math.h"
+#include "sapclassbasic.h"
+#include
+
+//////////////////////////////////////////////////////////////////////////////
+// Error codes
+//
+#define ERR_UNKNOWN_MODE 102
+
+class SequenceThread;
+
+class TestCamera : public CCameraBase
+{
+public:
+ TestCamera();
+ ~TestCamera();
+
+ // MMDevice API
+ // ------------
+ int Initialize();
+ int Shutdown();
+
+ void GetName(char* name) const;
+
+ // TestCamera API
+ // ------------
+ int SnapImage();
+ const unsigned char* GetImageBuffer();
+ unsigned GetImageWidth() const;
+ unsigned GetImageHeight() const;
+ unsigned GetImageBytesPerPixel() const;
+ unsigned GetBitDepth() const;
+ long GetImageBufferSize() const;
+ double GetExposure() const;
+ void SetExposure(double exp);
+ int SetROI(unsigned x, unsigned y, unsigned xSize, unsigned ySize);
+ int GetROI(unsigned& x, unsigned& y, unsigned& xSize, unsigned& ySize);
+ int ClearROI();
+ int PrepareSequenceAcqusition();
+ int StartSequenceAcquisition(double interval);
+ int StartSequenceAcquisition(long numImages, double interval_ms, bool stopOnOverflow);
+ int StopSequenceAcquisition();
+ bool IsCapturing();
+ int GetBinning() const;
+ int SetBinning(int binSize);
+ int IsExposureSequenceable(bool& seq) const {seq = false; return DEVICE_OK;}
+
+ // action interface
+ // ----------------
+ int OnBinning(MM::PropertyBase* pProp, MM::ActionType eAct);
+ int OnPixelType(MM::PropertyBase* pProp, MM::ActionType eAct);
+ int OnGain(MM::PropertyBase* pProp, MM::ActionType eAct);
+
+private:
+ friend class SequenceThread;
+ static const int IMAGE_WIDTH = 1920;
+ static const int IMAGE_HEIGHT = 1200;
+ static const int MAX_BIT_DEPTH = 12;
+
+ SequenceThread* thd_;
+ int binning_;
+ int bytesPerPixel_;
+ int bitsPerPixel_;
+ double gain_;
+ double exposureMs_;
+ bool initialized_;
+ ImgBuffer img_;
+ int roiX_, roiY_;
+ bool sequenceRunning_;
+
+ int ResizeImageBuffer();
+ void GenerateImage();
+ int InsertImage();
+
+ UINT32 acqDeviceNumber_;
+ char* acqServerName_;
+ char* configFilename_;
+ SapAcquisition Acq_;
+ SapAcqDevice AcqDevice_;
+ SapBufferWithTrash Buffers_;
+ SapTransfer AcqToBuf_;
+ SapTransfer AcqDeviceToBuf_;
+ SapTransfer* Xfer_;
+ SapLocation loc_;
+ SapFeature SapGain_;
+ int SapFormatBytes_;
+
+ int FreeHandles();
+ int ErrorBox(LPCWSTR text, LPCWSTR caption);
+ LPCWSTR TestCamera::string2winstring(const std::string& s);
+ int SapBufferReformat(SapFormat format, const char * acqFormat);
+};
+
+
+//threading stuff. Tread lightly
+class SequenceThread : public MMDeviceThreadBase
+{
+ public:
+ SequenceThread(TestCamera* pCam) : stop_(false), numImages_(0) {camera_ = pCam;}
+ ~SequenceThread() {}
+
+ int svc (void);
+
+ void Stop() {stop_ = true;}
+
+ void Start()
+ {
+ stop_ = false;
+ activate();
+ }
+
+ void SetLength(long images) {numImages_ = images;}
+ long GetLength(void) {return numImages_;};
+
+ private:
+ TestCamera* camera_;
+ bool stop_;
+ long numImages_;
+};
+
+#endif //_TestCamera_H_
diff --git a/MMDevice/MMDevice-SharedRuntime.vcxproj b/MMDevice/MMDevice-SharedRuntime.vcxproj
index 4c6560ae50..6a0d69fba2 100644
--- a/MMDevice/MMDevice-SharedRuntime.vcxproj
+++ b/MMDevice/MMDevice-SharedRuntime.vcxproj
@@ -43,31 +43,32 @@
{B8C95F39-54BF-40A9-807B-598DF2821D55}
Win32Proj
MMDeviceSharedRuntime
+ 10.0
StaticLibrary
true
MultiByte
- Windows7.1SDK
+ v142
StaticLibrary
true
MultiByte
- Windows7.1SDK
+ v142
StaticLibrary
false
MultiByte
- Windows7.1SDK
+ v142
StaticLibrary
false
MultiByte
- Windows7.1SDK
+ v142
@@ -141,4 +142,4 @@
-
+
\ No newline at end of file
diff --git a/micromanager.sln b/micromanager.sln
index 33156f5241..314d3ef05c 100644
--- a/micromanager.sln
+++ b/micromanager.sln
@@ -1,5 +1,7 @@
-Microsoft Visual Studio Solution File, Format Version 11.00
-# Visual C++ Express 2010
+Microsoft Visual Studio Solution File, Format Version 12.00
+# Visual Studio Version 16
+VisualStudioVersion = 16.0.30309.148
+MinimumVisualStudioVersion = 10.0.40219.1
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "MMCore", "MMCore\MMCore.vcxproj", "{36571628-728C-4ACD-A47F-503BA91C5D43}"
EndProject
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "MMCoreJ_wrap", "MMCoreJ_wrap\MMCoreJ_wrap.vcxproj", "{EFA68887-8A97-49D7-BAB4-768E15A4E597}"
@@ -454,7 +456,9 @@ Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "Skyra", "DeviceAdapters\Sky
EndProject
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "CoboltOfficial", "DeviceAdapters\CoboltOfficial\CoboltOfficial.vcxproj", "{7074BB23-A32B-4CD5-B77E-9EF4E24416BD}"
EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "BDPathway", "DeviceAdapters\BDPathway\BDPathway.vcxproj", "{AC358657-0C2B-41B6-97C1-1EFB8481D82A}"
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "BDPathway", "DeviceAdapters\BDPathway\BDPathway.vcxproj", "{E376977B-2B54-4745-9FE1-DDF726AD376F}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "GigENano", "DeviceAdapters\TeledyneDalsaGigE\GigENano.vcxproj", "{DE209272-1DA7-4551-9D34-3ECE99DDE827}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
@@ -2607,18 +2611,26 @@ Global
{63DEA291-B595-447A-8C7F-D32AFDA11DFD}.Release|x64.Build.0 = Release|x64
{805A53D5-1E00-42D7-96F0-661AC7D042A6}.Debug|Mixed Platforms.ActiveCfg = Debug|x64
{805A53D5-1E00-42D7-96F0-661AC7D042A6}.Debug|Mixed Platforms.Build.0 = Debug|x64
+ {805A53D5-1E00-42D7-96F0-661AC7D042A6}.Debug|Win32.ActiveCfg = Debug|Win32
+ {805A53D5-1E00-42D7-96F0-661AC7D042A6}.Debug|Win32.Build.0 = Debug|Win32
{805A53D5-1E00-42D7-96F0-661AC7D042A6}.Debug|x64.ActiveCfg = Debug|x64
{805A53D5-1E00-42D7-96F0-661AC7D042A6}.Debug|x64.Build.0 = Debug|x64
{805A53D5-1E00-42D7-96F0-661AC7D042A6}.Release|Mixed Platforms.ActiveCfg = Release|x64
{805A53D5-1E00-42D7-96F0-661AC7D042A6}.Release|Mixed Platforms.Build.0 = Release|x64
+ {805A53D5-1E00-42D7-96F0-661AC7D042A6}.Release|Win32.ActiveCfg = Release|Win32
+ {805A53D5-1E00-42D7-96F0-661AC7D042A6}.Release|Win32.Build.0 = Release|Win32
{805A53D5-1E00-42D7-96F0-661AC7D042A6}.Release|x64.ActiveCfg = Release|x64
{805A53D5-1E00-42D7-96F0-661AC7D042A6}.Release|x64.Build.0 = Release|x64
{ED3E2C21-ADA8-446D-8951-26F1E6E9F4DC}.Debug|Mixed Platforms.ActiveCfg = Debug|x64
{ED3E2C21-ADA8-446D-8951-26F1E6E9F4DC}.Debug|Mixed Platforms.Build.0 = Debug|x64
+ {ED3E2C21-ADA8-446D-8951-26F1E6E9F4DC}.Debug|Win32.ActiveCfg = Debug|Win32
+ {ED3E2C21-ADA8-446D-8951-26F1E6E9F4DC}.Debug|Win32.Build.0 = Debug|Win32
{ED3E2C21-ADA8-446D-8951-26F1E6E9F4DC}.Debug|x64.ActiveCfg = Debug|x64
{ED3E2C21-ADA8-446D-8951-26F1E6E9F4DC}.Debug|x64.Build.0 = Debug|x64
{ED3E2C21-ADA8-446D-8951-26F1E6E9F4DC}.Release|Mixed Platforms.ActiveCfg = Release|x64
{ED3E2C21-ADA8-446D-8951-26F1E6E9F4DC}.Release|Mixed Platforms.Build.0 = Release|x64
+ {ED3E2C21-ADA8-446D-8951-26F1E6E9F4DC}.Release|Win32.ActiveCfg = Release|Win32
+ {ED3E2C21-ADA8-446D-8951-26F1E6E9F4DC}.Release|Win32.Build.0 = Release|Win32
{ED3E2C21-ADA8-446D-8951-26F1E6E9F4DC}.Release|x64.ActiveCfg = Release|x64
{ED3E2C21-ADA8-446D-8951-26F1E6E9F4DC}.Release|x64.Build.0 = Release|x64
{97768FFD-1616-4CA5-902A-2F128118CC39}.Debug|Mixed Platforms.ActiveCfg = Debug|x64
@@ -3143,20 +3155,35 @@ Global
{7074BB23-A32B-4CD5-B77E-9EF4E24416BD}.Release|Win32.Build.0 = Release|Win32
{7074BB23-A32B-4CD5-B77E-9EF4E24416BD}.Release|x64.ActiveCfg = Release|x64
{7074BB23-A32B-4CD5-B77E-9EF4E24416BD}.Release|x64.Build.0 = Release|x64
- {AC358657-0C2B-41B6-97C1-1EFB8481D82A}.Debug|Mixed Platforms.ActiveCfg = Debug|x64
- {AC358657-0C2B-41B6-97C1-1EFB8481D82A}.Debug|Mixed Platforms.Build.0 = Debug|x64
- {AC358657-0C2B-41B6-97C1-1EFB8481D82A}.Debug|Win32.ActiveCfg = Debug|Win32
- {AC358657-0C2B-41B6-97C1-1EFB8481D82A}.Debug|Win32.Build.0 = Debug|Win32
- {AC358657-0C2B-41B6-97C1-1EFB8481D82A}.Debug|x64.ActiveCfg = Debug|x64
- {AC358657-0C2B-41B6-97C1-1EFB8481D82A}.Debug|x64.Build.0 = Debug|x64
- {AC358657-0C2B-41B6-97C1-1EFB8481D82A}.Release|Mixed Platforms.ActiveCfg = Release|x64
- {AC358657-0C2B-41B6-97C1-1EFB8481D82A}.Release|Mixed Platforms.Build.0 = Release|x64
- {AC358657-0C2B-41B6-97C1-1EFB8481D82A}.Release|Win32.ActiveCfg = Release|Win32
- {AC358657-0C2B-41B6-97C1-1EFB8481D82A}.Release|Win32.Build.0 = Release|Win32
- {AC358657-0C2B-41B6-97C1-1EFB8481D82A}.Release|x64.ActiveCfg = Release|x64
- {AC358657-0C2B-41B6-97C1-1EFB8481D82A}.Release|x64.Build.0 = Release|x64
+ {E376977B-2B54-4745-9FE1-DDF726AD376F}.Debug|Mixed Platforms.ActiveCfg = Debug|Win32
+ {E376977B-2B54-4745-9FE1-DDF726AD376F}.Debug|Mixed Platforms.Build.0 = Debug|Win32
+ {E376977B-2B54-4745-9FE1-DDF726AD376F}.Debug|Win32.ActiveCfg = Debug|Win32
+ {E376977B-2B54-4745-9FE1-DDF726AD376F}.Debug|Win32.Build.0 = Debug|Win32
+ {E376977B-2B54-4745-9FE1-DDF726AD376F}.Debug|x64.ActiveCfg = Debug|x64
+ {E376977B-2B54-4745-9FE1-DDF726AD376F}.Debug|x64.Build.0 = Debug|x64
+ {E376977B-2B54-4745-9FE1-DDF726AD376F}.Release|Mixed Platforms.ActiveCfg = Release|Win32
+ {E376977B-2B54-4745-9FE1-DDF726AD376F}.Release|Mixed Platforms.Build.0 = Release|Win32
+ {E376977B-2B54-4745-9FE1-DDF726AD376F}.Release|Win32.ActiveCfg = Release|Win32
+ {E376977B-2B54-4745-9FE1-DDF726AD376F}.Release|Win32.Build.0 = Release|Win32
+ {E376977B-2B54-4745-9FE1-DDF726AD376F}.Release|x64.ActiveCfg = Release|x64
+ {E376977B-2B54-4745-9FE1-DDF726AD376F}.Release|x64.Build.0 = Release|x64
+ {DE209272-1DA7-4551-9D34-3ECE99DDE827}.Debug|Mixed Platforms.ActiveCfg = Debug|Win32
+ {DE209272-1DA7-4551-9D34-3ECE99DDE827}.Debug|Mixed Platforms.Build.0 = Debug|Win32
+ {DE209272-1DA7-4551-9D34-3ECE99DDE827}.Debug|Win32.ActiveCfg = Debug|Win32
+ {DE209272-1DA7-4551-9D34-3ECE99DDE827}.Debug|Win32.Build.0 = Debug|Win32
+ {DE209272-1DA7-4551-9D34-3ECE99DDE827}.Debug|x64.ActiveCfg = Debug|x64
+ {DE209272-1DA7-4551-9D34-3ECE99DDE827}.Debug|x64.Build.0 = Debug|x64
+ {DE209272-1DA7-4551-9D34-3ECE99DDE827}.Release|Mixed Platforms.ActiveCfg = Release|Win32
+ {DE209272-1DA7-4551-9D34-3ECE99DDE827}.Release|Mixed Platforms.Build.0 = Release|Win32
+ {DE209272-1DA7-4551-9D34-3ECE99DDE827}.Release|Win32.ActiveCfg = Release|Win32
+ {DE209272-1DA7-4551-9D34-3ECE99DDE827}.Release|Win32.Build.0 = Release|Win32
+ {DE209272-1DA7-4551-9D34-3ECE99DDE827}.Release|x64.ActiveCfg = Release|x64
+ {DE209272-1DA7-4551-9D34-3ECE99DDE827}.Release|x64.Build.0 = Release|x64
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
EndGlobalSection
+ GlobalSection(ExtensibilityGlobals) = postSolution
+ SolutionGuid = {375A63CA-A41F-40F1-B15E-C67A6A1A5DA2}
+ EndGlobalSection
EndGlobal