From ead101a5612e2a3bb863366c212c4b6275f30f7e Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Mon, 27 Jun 2022 19:22:59 -0700 Subject: [PATCH 01/29] add MeadowlarkLC device adapter --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp | 2855 +++++++++++++++++ DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h | 209 ++ .../MeadowlarkLC/MeadowlarkLC.vcxproj | 175 + micromanager.sln | 7 + 4 files changed, 3246 insertions(+) create mode 100644 DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp create mode 100644 DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h create mode 100644 DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp new file mode 100644 index 000000000..6923450e3 --- /dev/null +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp @@ -0,0 +1,2855 @@ +/////////////////////////////////////////////////////////////////////////////// +// FILE: MeadowlarkLC.cpp +// PROJECT: Micro-Manager +// SUBSYSTEM: DeviceAdapters +//----------------------------------------------------------------------------- +// DESCRIPTION: MeadowlarkLC Device Adapter for Four Channel Digital Interface (D3050) and API family +// +// Copyright � 2009 - 2018, Marine Biological Laboratory +// +// LICENSE (Berkeley Software Distribution License): Redistribution and use in source and binary forms, +// with or without modification, are permitted provided that the following conditions are met: +// +// 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. +// 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer +// in the documentation and/or other materials provided with the distribution. +// 3. Neither the name of the Marine Biological Laboratory nor the names of its contributors may be used to endorse or promote products +// derived from this software without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE +// COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +// (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +// HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) +// ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +// +// The views and conclusions contained in the software and documentation are those of the authors and should not be interpreted as +// representing official policies, either expressed or implied, of any organization. +// +// Developed at the Laboratory of Rudolf Oldenbourg at the Marine Biological Laboratory in Woods Hole, MA. +// LAST UPDATE: Amitabh Verma, MBL - Aug. 21, 2018 +// +// +// AUTHOR: Amitabh Verma, MBL - Dec. 05, 2012 +// +// Issue tracker :---> http://www.openpolscope.org/mantis/ +// ToDo List at EOF +// +// Change Log - Amitabh Verma - Aug. 21, 2018 - 1.00.03 +// 1. Implemented config file for device adapter that gets written out when not found based on serial number of device. +// This config file can be updated with palette element values for different wavelengths and can be set using command eg. "sp 546" +// The first defined palette in the csv file is loaded as default at startup when the device driver is loaded. +// +// Change Log - Amitabh Verma - Aug. 06, 2018 - 1.00.02 +// 1. Option for LC - File (Serial_No.csv) +// Note: This method will allow providing LCs with individual custom calibration curves and also allow multiple instances of the adapter to +// load individual calibration curves based on the device Serial No. +// +// Change Log - Amitabh Verma - Oct. 10, 2014 +// 1. Option for LC - Loaded From File (mmgr_dal_MeadowlarkLC.csv) +// Note: This method will allow providing LCs with custom calibration curve and no further need to recompile this device adapter +// with additional calibration curves. +// +// Change Log - Amitabh Verma - July. 24, 2014 +// 1. Replaced ',' comma with ';' semi-colon in property names due to Micro-Manager warning during HW Config Wizard 'Contains reserved chars' +// Note: This will break Pol-Acquisition (OpenPolScope) and requires compatible version which uses same name for Property +// +// Change Log +// March 19, 2014 +// 1. Absolute retardance field +// 2. Extended retardance range to minimum based on voltage and maximum 1.6 waves +// 3. changedTime_ is called only when setting voltage - not for other operations +// +// Feb. 10, 2014 +// 1. Added support for D5020 (20V) Controller. Tested with actual unit. +// - Set Max no. of LC based on controller type. +// - Check for no. of Active LCs less than Max +// +// Nov. 21, 2013 +// 1. Calibration curves now part of dll and embedded as resource +// - To add more curves add in resource.h and MeadownlarkLC.rc and then add selection case for LC Type and under Initialize() +// +// Nov. 19, 2013 +// 1. Added LC Calibration curve selection option +// +// Nov. 18, 2013 +// 1. Added scaling based of Controller type (D3050, D3060HV, D5020) +// +// Nov. 14, 2013 +// 1. Support for 20V controller - untested (D5020) +// 2. Added TNE support with defaults 20ms pluse duration with 10V/20V Amplitude +// 3. Added Exercise LC Code +// 4a. Added characterization for 10V and 20V range device +// 4b. Implemented range for Voltage and Retardance based on 10V/20V device +// +// June 27, 2013 +// 1. Load calibration curves via csv file +// 2. Generate interpolated calibration curves +// 3. Export calibration curve being used +// +// June 23, 2013 +// 1. MeadowlarkLC beta release version 1.0 +// +// Apr. 23, 2013 +// 1. MeadowlarkLC alpha release version 1.0 +// +// Dec. 05, 2012 +// 1. Implementing MeadowlarkLC from VariLC device adapter +// +// http://stackoverflow.com/questions/4200189/how-to-use-cmake-to-generate-vs-project-which-link-to-some-dll-files + + +#ifdef WIN32 +// #include +#define snprintf _snprintf +#endif + +#include +#include +#include +#include +#include +#include +#include +#include "usbdrvd.h" +#include +#include + + +//////// MeadowlarkLC ////////// +#include "MeadowlarkLC.h" +#include "resource.h" + +//////// Micro-manager interface ////////// +#include "ModuleInterface.h" + +////////////////////////////////////////////////////////////////////////////////////////// + +const char* g_ControllerName = "MeadowlarkLC"; +const char* g_ControllerAbout = "MeadowlarkLC Digital Device Controller/Interface"; +const char* g_ControllerDevices = "Select Device #"; +const char* g_ControllerDeviceType = "Select Device Interface"; +const char* g_ControllerDeviceType10V = "10V (D3050) Controller"; +const char* g_ControllerDeviceType20V_D3060HV = "20V (D3060HV) Controller"; +const char* g_ControllerDeviceType20V_D5020 = "20V (D5020) Controller"; +const double g_ControllerDeviceType10VFac = 6553.5; +const double g_ControllerDeviceType20VFac_D5020 = 1000; +const double g_ControllerDeviceType20VFac_D3060HV = 655.35; +const char* g_ControllerTotalLCs = "Total Number of LCs"; + +const double g_ControllerDeviceRetardanceLowLimit = 0.001; +const double g_ControllerDeviceRetardanceHighLimit = 1.6; + +const double g_ControllerDeviceRetardanceAbsRetLow = 0.0; +const double g_ControllerDeviceRetardanceAbsRetHigh = 1200.0; + +const char* g_ControllerLCType_Internal = "Internal (Single generic 546nm curve)"; +const char* g_ControllerLCType_Paired = "Use LC Paired with Controller"; +const char* g_ControllerLCType_F001 = "File (mmgr_dal_MeadowlarkLC.csv)"; //"Loaded From File (mmgr_dal_MeadowlarkLC.csv)"; +const char* g_ControllerLCType_F001b = "Loaded From File (mmgr_dal_MeadowlarkLC.csv)"; // retained for backward compatibility +const char* g_ControllerLCType_F002 = "File (SERIAL_NO.csv)"; //"Loaded From File (SERIAL_NO.csv)"; +const char* g_ControllerLCType_B001 = "B001 (Non-Bonded)"; //"Non-Bonded LC Type"; +const char* g_ControllerLCType_B002 = "B002 (Bonded)"; // "Bonded LC Type"; +const char* g_ControllerLCType_T001 = "Thick 001 (Bonded)"; // "Thick Bonded LC Type"; + +const char* g_ControllerLCType_B14181 = "B14181"; // "Bonded LC Type"; // L13009 +const char* g_ControllerSN_L13009 = "L13009"; // "Bonded LC Type"; // B14181 (A14001 & B14022) + +const char* g_ControllerLCType_B14182 = "B14182"; // "Bonded LC Type"; // L13010 +const char* g_ControllerSN_L13010 = "L13010"; // "Bonded LC Type"; // B14182 (A14004 & B14021) + +const char* g_ControllerLCType_B14183 = "B14183"; // "Bonded LC Type"; // L13011 +const char* g_ControllerSN_L13011 = "L13011"; // "Bonded LC Type"; // B14183 (A14004 & A14006) + +const char* g_ControllerLCType_F001_Curves = "mmgr_dal_MeadowlarkLC.csv"; +const char* g_ControllerLCType_F002_Curves = ".csv"; +const char* g_ControllerLCType_1_Curves = "CURVE_IDR_0_1"; +const char* g_ControllerLCType_2_Curves = "CURVE_IDR_0_2"; +const char* g_ControllerLCType_T001_Curves = "CURVE_IDR_T001"; +const char* g_ControllerLCType_B14181_Curves = "CURVE_IDR_B14181"; +const char* g_ControllerLCType_B14182_Curves = "CURVE_IDR_B14182"; +const char* g_ControllerLCType_B14183_Curves = "CURVE_IDR_B14183"; + +const char* g_ControllerDescription = "Description"; +const char* g_ControllerDescriptionInfo = "Description Info"; +const std::string g_Nonedetected = "None detected"; +const LPCSTR g_About = "MeadowlarkLC Device Adapter for Micro-Manager and use with OpenPolScope Micro-Manager plugin. \n Please refer to http://www.openpolscope.org for more information."; + +const char* g_Dev_Adapter_Ver = "1.00.03"; +using namespace std; + +const HMODULE GetCurrentModule() +{ + DWORD flags = GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS; + HMODULE hm = 0; + ::GetModuleHandleEx(flags, reinterpret_cast(GetCurrentModule), &hm); + return hm; +} + + +// Default config values will be used at startup +const double ConfigDataDefaults[5][3] = { + {546,0.25,0.5}, + {546,0.25,0.47}, + {546,0.25,0.53}, + {546,0.22,0.5}, + {546,0.28,0.5} +}; + +const int ArrayLengthDefault = 198; +// LC Calibration curve Voltage(mV) vs Absolute Retardance(nm) +const double ArrayDefaultLcVoltagesRet[ArrayLengthDefault][3] = { + {0,1284.343,1284.343}, + {200,1284.411,1284.411}, + {400,1284.0869,1284.0869}, + {600,1283.8796,1283.8796}, + {800,1283.3625,1283.3625}, + {800.0002,1283.2228,1283.2228}, + {800.0005,1283.3013,1283.3013}, + {800.0013,1283.415,1283.415}, + {800.0025,1283.3468,1283.3468}, + {800.0045,1283.4783,1283.4783}, + {800.0074,1283.3376,1283.3376}, + {800.0117,1283.3345,1283.3345}, + {800.0179,1283.4308,1283.4308}, + {800.0264,1283.496,1283.496}, + {800.0377,1283.4891,1283.4891}, + {800.0527,1283.4348,1283.4348}, + {800.0721,1283.7001,1283.7001}, + {800.0969,1283.6556,1283.6556}, + {800.128,1283.7085,1283.7085}, + {800.1666,1283.7365,1283.7365}, + {800.214,1283.7697,1283.7697}, + {800.2716,1283.6506,1283.6506}, + {800.3411,1283.7167,1283.7167}, + {800.424,1283.6982,1283.6982}, + {800.5223,1283.7743,1283.7743}, + {800.638,1283.8627,1283.8627}, + {800.7734,1283.7518,1283.7518}, + {800.9308,1283.8488,1283.8488}, + {801.113,1283.8833,1283.8833}, + {801.3225,1283.8304,1283.8304}, + {801.5625,1283.8893,1283.8893}, + {801.8361,1283.8992,1283.8992}, + {802.1468,1283.9257,1283.9257}, + {802.4982,1283.9562,1283.9562}, + {802.8941,1284.0687,1284.0687}, + {803.3387,1284.1172,1284.1172}, + {803.8364,1284.0798,1284.0798}, + {804.3917,1284.0042,1284.0042}, + {805.0095,1284.047,1284.047}, + {805.6949,1284.0695,1284.0695}, + {806.4534,1284.1594,1284.1594}, + {807.2906,1284.1851,1284.1851}, + {808.2125,1284.1339,1284.1339}, + {809.2255,1284.2399,1284.2399}, + {810.336,1284.2579,1284.2579}, + {811.5509,1284.3578,1284.3578}, + {812.8775,1284.1702,1284.1702}, + {814.3233,1284.2469,1284.2469}, + {815.8961,1284.1438,1284.1438}, + {817.6041,1284.283,1284.283}, + {819.4559,1284.301,1284.301}, + {821.4603,1284.2782,1284.2782}, + {823.6266,1284.1348,1284.1348}, + {825.9644,1284.2441,1284.2441}, + {828.4838,1284.1818,1284.1818}, + {831.1949,1284.3066,1284.3066}, + {834.1088,1284.2123,1284.2123}, + {837.2363,1284.1847,1284.1847}, + {840.5892,1284.2885,1284.2885}, + {844.1794,1284.2258,1284.2258}, + {848.0192,1284.1924,1284.1924}, + {852.1216,1284.3458,1284.3458}, + {856.4996,1284.1655,1284.1655}, + {861.1669,1284.0703,1284.0703}, + {866.1377,1284.145,1284.145}, + {871.4266,1284.1002,1284.1002}, + {877.0485,1284.0598,1284.0598}, + {883.0189,1284.0197,1284.0197}, + {889.3539,1283.9844,1283.9844}, + {896.0698,1283.9204,1283.9204}, + {903.1836,1283.9547,1283.9547}, + {910.7126,1283.9744,1283.9744}, + {918.675,1283.9253,1283.9253}, + {927.0889,1283.9131,1283.9131}, + {935.9734,1283.7408,1283.7408}, + {945.3481,1283.6477,1283.6477}, + {955.2328,1283.6884,1283.6884}, + {965.6481,1283.6045,1283.6045}, + {976.6151,1283.4708,1283.4708}, + {988.1553,1283.4731,1283.4731}, + {1000.2911,1283.4991,1283.4991}, + {1013.0452,1283.2888,1283.2888}, + {1026.4408,1283.2068,1283.2068}, + {1040.502,1282.854,1282.854}, + {1055.2531,1282.8246,1282.8246}, + {1070.7194,1282.4509,1282.4509}, + {1086.9263,1282.1366,1282.1366}, + {1103.9004,1281.6805,1281.6805}, + {1121.6683,1281.3497,1281.3497}, + {1140.2579,1280.9851,1280.9851}, + {1159.6971,1280.6768,1280.6768}, + {1180.0148,1280.2689,1280.2689}, + {1201.2404,1279.3618,1279.3618}, + {1223.4039,1278.7089,1278.7089}, + {1246.5363,1277.9419,1277.9419}, + {1270.6688,1276.0315,1276.0315}, + {1295.8336,1274.8234,1274.8234}, + {1322.0635,1272.7963,1272.7963}, + {1349.3917,1270.1302,1270.1302}, + {1377.8527,1266.1652,1266.1652}, + {1407.4811,1260.8419,1260.8419}, + {1438.3125,1253.3003,1253.3003}, + {1470.3833,1244.5061,1244.5061}, + {1503.7303,1232.5726,1232.5726}, + {1538.3914,1217.3304,1217.3304}, + {1574.4049,1198.2084,1198.2084}, + {1611.8101,1176.7759,1176.7759}, + {1650.6469,1154.4043,1154.4043}, + {1690.9559,1128.3533,1128.3533}, + {1732.7789,1089,1089}, + {1821.1359,1047.5177,1047.5177}, + {1867.7567,1016.2104,1016.2104}, + {1916.0651,984.7769,984.7769}, + {1966.1063,953.2874,953.2874}, + {2017.9265,920.6101,920.6101}, + {2071.573,887.09,887.09}, + {2127.0933,851.7007,851.7007}, + {2184.5361,816.75,816.75}, + {2305.3887,754.0078,754.0078}, + {2368.8997,721.3992,721.3992}, + {2434.5366,689.3527,689.3527}, + {2502.3521,658.8939,658.8939}, + {2572.3999,628.5602,628.5602}, + {2644.7349,599.2983,599.2983}, + {2719.4126,569.1844,569.1844}, + {2796.4893,544.5,544.5}, + {2958.0703,491.2751,491.2751}, + {3042.6919,468.1365,468.1365}, + {3129.9478,446.146,446.146}, + {3219.8982,425.1326,425.1326}, + {3312.6057,405.4332,405.4332}, + {3408.1331,387.0562,387.0562}, + {3506.5439,369.5298,369.5298}, + {3607.9033,353.7877,353.7877}, + {3712.2771,338.264,338.264}, + {3819.7314,324.5506,324.5506}, + {3930.3347,308.7356,308.7356}, + {4044.1553,296.194,296.194}, + {4161.2627,284.466,284.466}, + {4281.728,272.25,272.25}, + {4533.0195,249.2416,249.2416}, + {4663.9917,240.8623,240.8623}, + {4798.6152,231.4884,231.4884}, + {4936.9644,221.9211,221.9211}, + {5079.1172,214.1089,214.1089}, + {5225.1514,206.1059,206.1059}, + {5375.145,199.4312,199.4312}, + {5529.1787,192.4627,192.4627}, + {5687.3335,186.2214,186.2214}, + {5849.6919,179.7628,179.7628}, + {6016.3364,173.8859,173.8859}, + {6187.3521,168.3429,168.3429}, + {6362.8232,162.9014,162.9014}, + {6542.8379,157.5549,157.5549}, + {6727.4824,152.6496,152.6496}, + {6916.8462,147.6369,147.6369}, + {7111.019,143.0052,143.0052}, + {7310.0918,138.6415,138.6415}, + {7514.1567,134.3855,134.3855}, + {7723.3071,130.3516,130.3516}, + {7937.6372,126.2824,126.2824}, + {8157.2432,122.406,122.406}, + {8382.2217,118.8456,118.8456}, + {8612.6699,115.4299,115.4299}, + {8848.6885,111.6104,111.6104}, + {9090.377,108.5394,108.5394}, + {9337.8359,105.2933,105.2933}, + {9591.1699,102.3992,102.3992}, + {9850.4814,99.3358,99.3358}, + {10115.876,96.4839,96.4839}, + {10387.4609,93.7825,93.7825}, + {10665.3428,91.202,91.202}, + {10949.6318,88.5837,88.5837}, + {11240.4365,86.0813,86.0813}, + {11537.8691,83.6826,83.6826}, + {11842.042,81.2935,81.2935}, + {12153.0684,79.0205,79.0205}, + {12471.0654,76.9506,76.9506}, + {12796.1484,75.0336,75.0336}, + {13128.4346,72.9454,72.9454}, + {13468.0439,70.8509,70.8509}, + {13815.0967,69.1639,69.1639}, + {14169.7139,67.2585,67.2585}, + {14532.0195,65.5513,65.5513}, + {14902.1367,63.9257,63.9257}, + {15280.1924,61.706,61.706}, + {15666.3135,60.4764,60.4764}, + {16060.627,58.9538,58.9538}, + {16463.2637,57.8524,57.8524}, + {16874.3535,55.6492,55.6492}, + {17294.0312,54.4416,54.4416}, + {17722.4277,53.0858,53.0858}, + {18159.6816,51.6723,51.6723}, + {18605.9258,50.635,50.635}, + {19061.3008,49.3032,49.3032}, + {19525.9453,47.6384,47.6384}, + {20000,46.83,46.83} + +}; + +/////////////////////////////////////////////////////////////////////////////// +// Exported MMDevice API +/////////////////////////////////////////////////////////////////////////////// +MODULE_API void InitializeModuleData() +{ + RegisterDevice(g_ControllerName, MM::GenericDevice, g_ControllerAbout); + //AddAvailableDeviceName(g_ControllerName, g_ControllerAbout); +} + +MODULE_API MM::Device* CreateDevice(const char* deviceName) +{ + if (deviceName == 0) return 0; + if (strcmp(deviceName, g_ControllerName) == 0) + { + return new MeadowlarkLC(); + } + return 0; +} + +MODULE_API void DeleteDevice(MM::Device* pDevice) +{ + delete pDevice; +} + +/////////////////////////////////////////////////////////////////////////////// +// MeadowlarkLC Hub +/////////////////////////////////////////////////////////////////////////////// + +MeadowlarkLC::MeadowlarkLC() : + + answerTimeoutMs_(1000), + initialized_(false), + interruptExercise_(false), + tneDuration_(0), + tneAmplitude_(0), + numActiveLCs_(2), + // numTotalLCs_(4), + numPalEls_(5), + cur_dev_name("0"), + cur_dev(0), + g_ControllerDeviceTypeVFac(0), + VoltageToRetFactor(0), + RetToVoltageFactor(0), + wavelength_(546.0), // the cached value + numberofCurves(1), // default is 1, will change based on import + activationKey_("OPS-MeadowlarkLcOpenSource"), + ArrayLength2(198) + +{ + cur_dev = 0; + controllerType_ = g_ControllerDeviceType20V_D5020; // default to D5020 + controllerLCType_ = g_ControllerLCType_F002; // USE FILE.csv by Default + description_ = "Not found"; + serialnum_ = "Undefined"; + cur_dev_name = "1"; + + loadDefault(); + InitializeDefaultErrorMessages(); + // add custom messages + + SetErrorText(ERR_PORT_CHANGE_FORBIDDEN, "You can't change the port after device has been initialized."); + SetErrorText(ERR_INVALID_DEVICE, "The selected plugin does not fit for the device."); + SetErrorText(ERR_INVALID_SERIAL_NUMBER, "Invalid Serial Number. Please refer to your Meadowlark device unit."); + SetErrorText(ERR_INVALID_LCSERIAL_NUMBER, "Invalid LC-Serial Number. Calibration curve for this LC does not exist."); + SetErrorText(ERR_INVALID_ACTIVATION_KEY, "Invalid Activation Key. Please refer to your Meadowlark device unit."); + SetErrorText(ERR_INVALID_LC_UNPAIRED, "Invalid LC-Controller Pair. This Controller is not paired with an LC. Enter LC-S/N"); + if (controllerLCType_ == g_ControllerLCType_F002) { + SetErrorText(ERR_INVALID_LC_FILE, ".csv File Invalid Selection. The calibration curve file does not exist or is invalid."); + } + else { + SetErrorText(ERR_INVALID_LC_SELECTION, "Invalid Selection. The calibration curve file (mmgr_dal_MeadowlarkLC.csv) does not exist or is invalid."); + } + + std::string str = IntToString(numTotalLCs_).c_str(); + totalLCsMsg = "Invalid Active LCs. Number of Active LCs cannot be more than Total of " + str + " LCs"; + SetErrorText(ERR_INVALID_ACTIVE_LCS, totalLCsMsg.c_str()); + + // pre-initialization properties + + // Description from device + CPropertyAction* pAct = new CPropertyAction(this, &MeadowlarkLC::GetDesc); + CreateProperty(g_ControllerDescriptionInfo, description_.c_str(), MM::String, false, pAct, true); + + // Select device # + pAct = new CPropertyAction(this, &MeadowlarkLC::OnNumDevices); + CreateProperty(g_ControllerDevices, g_Nonedetected.c_str(), MM::String, false, pAct, true); + + EnableDelay(); + + theGUID.Data1 = 0xa22b5b8b; + theGUID.Data2 = 0xc670; + theGUID.Data3 = 0x4198; + theGUID.Data4[0] = 0x93; + theGUID.Data4[1] = 0x85; + theGUID.Data4[2] = 0xaa; + theGUID.Data4[3] = 0xba; + theGUID.Data4[4] = 0x9d; + theGUID.Data4[5] = 0xfc; + theGUID.Data4[6] = 0x7d; + theGUID.Data4[7] = 0x2b; + + USB_PID = 0x139C; + devcnt = USBDRVD_GetDevCount(USB_PID); + + BYTE ver_cmd[] = { 'v', 'e', 'r', ':', '?', '\n' }; + BYTE status[64]; + // description_[64]; + + int devCount = devcnt; + + UINT pipeCount = 0; + int pipeCountInt = pipeCount; + + ClearAllowedValues(g_ControllerDevices); // clear old vals + + if (devCount > 0) { + + for (int devIdx = 1; devIdx < (devCount + 1); devIdx++) + { + dev_Handle = USBDRVD_OpenDevice(devIdx, flagsandattrs, USB_PID); // get the device handle + pipe0 = USBDRVD_PipeOpen(1, 0, flagsandattrs, &theGUID); + pipe1 = USBDRVD_PipeOpen(1, 1, flagsandattrs, &theGUID); + + USBDRVD_BulkWrite(dev_Handle, 1, ver_cmd, sizeof(ver_cmd)); /* send ver:? command */ + USBDRVD_BulkRead(dev_Handle, 0, status, sizeof(status)); /* read status response */ + + /* output status until a is found */ + std::string device = IntToString(devIdx); + std::string temp = ((char*)status); + + if (dev_Handle >= 0) { + AddAllowedValue(g_ControllerDevices, device.c_str()); + devNameList.push_back(device.c_str()); + descriptionUnparsed_ = temp + '\n'; + description_ = temp; + description_ = RemoveChars(description_, "."); + description_ = RemoveChars(description_, ","); + cur_dev_name = device; + + pipeCount = USBDRVD_GetPipeCount(dev_Handle); + pipeCountInt = pipeCount; + } + + USBDRVD_CloseDevice(dev_Handle); + } + + SetProperty(g_ControllerDevices, cur_dev_name.c_str()); + + // LC Controller Type + pAct = new CPropertyAction(this, &MeadowlarkLC::OnControllerType); + CreateProperty(g_ControllerDeviceType, g_ControllerDeviceType10V, MM::String, false, pAct, true); + AddAllowedValue(g_ControllerDeviceType, g_ControllerDeviceType10V); + AddAllowedValue(g_ControllerDeviceType, g_ControllerDeviceType20V_D3060HV); + AddAllowedValue(g_ControllerDeviceType, g_ControllerDeviceType20V_D5020); + + // LC (Non-Bonded, Bonded, etc...) + pAct = new CPropertyAction(this, &MeadowlarkLC::OnControllerLCType); + CreateProperty("Select LC Type", g_ControllerLCType_Paired, MM::String, false, pAct, true); + AddAllowedValue("Select LC Type", g_ControllerLCType_Paired); + AddAllowedValue("Select LC Type", g_ControllerLCType_B001); + AddAllowedValue("Select LC Type", g_ControllerLCType_B002); + AddAllowedValue("Select LC Type", g_ControllerLCType_B14181); + AddAllowedValue("Select LC Type", g_ControllerLCType_B14182); + AddAllowedValue("Select LC Type", g_ControllerLCType_B14183); + AddAllowedValue("Select LC Type", g_ControllerLCType_T001); + AddAllowedValue("Select LC Type", g_ControllerLCType_F001); + AddAllowedValue("Select LC Type", g_ControllerLCType_F001b); + AddAllowedValue("Select LC Type", g_ControllerLCType_F002); + + pAct = new CPropertyAction(this, &MeadowlarkLC::OnSerialNumber); + CreateProperty("Controller S/N", "Undefined", MM::String, false, pAct, true); + + pAct = new CPropertyAction(this, &MeadowlarkLC::OnActivationKey); + CreateProperty("Controller S/N-Activation Key", "Undefined", MM::String, true, pAct, true); + + pAct = new CPropertyAction(this, &MeadowlarkLC::OnNumTotalLCs); + CreateProperty(g_ControllerTotalLCs, "0", MM::Integer, true, pAct, true); + + pAct = new CPropertyAction(this, &MeadowlarkLC::OnNumActiveLCs); + CreateProperty("Number of Active LCs", "0", MM::Integer, false, pAct, true); + + pAct = new CPropertyAction(this, &MeadowlarkLC::OnNumPalEls); + CreateProperty("Total Number of Palette Elements", "5", MM::Integer, false, pAct, true); + } + else { + std::string device = "None detected"; + AddAllowedValue(g_ControllerDevices, device.c_str()); + devNameList.push_back(device.c_str()); + SetProperty(g_ControllerDevices, device.c_str()); + } +} + + +MeadowlarkLC::~MeadowlarkLC() +{ + Shutdown(); +} + +void MeadowlarkLC::GetName(char* name) const +{ + CDeviceUtils::CopyLimitedString(name, g_ControllerName); +} + +int MeadowlarkLC::Initialize() +{ + + if (cur_dev < 1) { + return DEVICE_NOT_CONNECTED; + } + + if (serialnum_ == "Undefined" || serialnum_ == "") { + return ERR_INVALID_SERIAL_NUMBER; + } + + setSystemSpecificActivationKey(serialnum_); + if (activationKey_ == "Undefined" || activationKey_ == "" || activationKey_ != SystemSpecificActivationKey) { + return ERR_INVALID_ACTIVATION_KEY; + } + + if (controllerLCType_ == g_ControllerLCType_Internal) { + return ERR_INVALID_LC_SELECTION; + } + + if (controllerLCType_ == g_ControllerLCType_Paired) { + if (serialnum_ == g_ControllerSN_L13009) { + controllerLCType_ = g_ControllerLCType_B14181; + + } + else if (serialnum_ == g_ControllerSN_L13010) { + controllerLCType_ = g_ControllerLCType_B14182; + + } + else if (serialnum_ == g_ControllerSN_L13011) { + controllerLCType_ = g_ControllerLCType_B14183; + + } + if (controllerLCType_ == g_ControllerLCType_Paired) { + return ERR_INVALID_LC_UNPAIRED; + } + } + if (controllerLCType_ == "Undefined" || controllerLCType_ == "") { + return ERR_INVALID_LCSERIAL_NUMBER; + } + + if (numActiveLCs_ > numTotalLCs_) { + std::string str = IntToString(numTotalLCs_).c_str(); + totalLCsMsg = "Invalid Active LCs. Number of Active LCs cannot be more than Total of " + str + " LCs"; + SetErrorText(ERR_INVALID_ACTIVE_LCS, totalLCsMsg.c_str()); + + return ERR_INVALID_ACTIVE_LCS; + } + + loadDefault(); + palEl_[numPalEls_]; + retardance_[numTotalLCs_]; + voltage_[numTotalLCs_]; + + for (long i = 0; i < numTotalLCs_; ++i) { + retardance_[i] = 0.5; + voltage_[i] = 555; + } + + for (long i = 0; i < numPalEls_; i++) { + + for (int i2 = 0; i2 < numActiveLCs_; i2++) { + palette_[i][i2] = 0.25; + } + string str; + for (int i2 = 0; i2 < numActiveLCs_; i2++) { + str = str + " " + DoubleToString(retardance_[i2]); + } + palEl_[i] = DoubleToString(wavelength_) + str; + } + + if (controllerType_ == g_ControllerDeviceType10V) { + g_ControllerDeviceTypeVFac = g_ControllerDeviceType10VFac; + tneAmplitude_ = 10; + } + else if (controllerType_ == g_ControllerDeviceType20V_D5020) { + g_ControllerDeviceTypeVFac = g_ControllerDeviceType20VFac_D5020; + tneAmplitude_ = 20; + } + else if (controllerType_ == g_ControllerDeviceType20V_D3060HV) { + g_ControllerDeviceTypeVFac = g_ControllerDeviceType20VFac_D3060HV; + tneAmplitude_ = 20; + } + + // load curve based on LC Type + controllerLcTypeChange(); + + initialized_ = true; + + dev_Handle = USBDRVD_OpenDevice(cur_dev, flagsandattrs, USB_PID); // get the device handle + + // Name + int ret = CreateProperty(MM::g_Keyword_Name, g_ControllerName, MM::String, true); + if (DEVICE_OK != ret) + return ret; + + // Select device # + ret = CreateProperty("Device ID", IntToString(cur_dev).c_str(), MM::String, true); + if (DEVICE_OK != ret) + return ret; + + // Description + ret = CreateProperty(MM::g_Keyword_Description, g_ControllerAbout, MM::String, true); + if (DEVICE_OK != ret) + return ret; + + // Description from device + ret = CreateProperty("Firmare Info", description_.c_str(), MM::String, true); + if (DEVICE_OK != ret) + return ret; + + // Version number + CPropertyAction* pAct = new CPropertyAction(this, &MeadowlarkLC::OnSerialNumber); + ret = CreateProperty("Version Number", "Version Number Not Found", MM::String, true, pAct); + if (ret != DEVICE_OK) + return ret; + + // Device Adapter Version number + pAct = new CPropertyAction(this, &MeadowlarkLC::OnDevAdapterSerialNumber); + ret = CreateProperty("Device Adapter Version Number", "Device Adapter Version Number Not Found", MM::String, true, pAct); + if (ret != DEVICE_OK) + return ret; + + // Controller Type + pAct = new CPropertyAction(this, &MeadowlarkLC::OnControllerType); + ret = CreateProperty("Controller Type", controllerType_.c_str(), MM::String, true, pAct); + if (ret != DEVICE_OK) + return ret; + + // Controller LC Type + pAct = new CPropertyAction(this, &MeadowlarkLC::OnControllerLCType); + ret = CreateProperty("Controller LC Type", controllerLCType_.c_str(), MM::String, false, pAct); + AddAllowedValue("Controller LC Type", g_ControllerLCType_Paired); + AddAllowedValue("Controller LC Type", g_ControllerLCType_B001); + AddAllowedValue("Controller LC Type", g_ControllerLCType_B002); + AddAllowedValue("Controller LC Type", g_ControllerLCType_B14181); + AddAllowedValue("Controller LC Type", g_ControllerLCType_B14182); + AddAllowedValue("Controller LC Type", g_ControllerLCType_B14183); + AddAllowedValue("Controller LC Type", g_ControllerLCType_T001); + AddAllowedValue("Controller LC Type", g_ControllerLCType_F001); + AddAllowedValue("Controller LC Type", g_ControllerLCType_F001b); + AddAllowedValue("Controller LC Type", g_ControllerLCType_F002); + AddAllowedValue("Controller LC Type", g_ControllerLCType_Internal); + if (ret != DEVICE_OK) + return ret; + + // Wavelength + pAct = new CPropertyAction(this, &MeadowlarkLC::OnWavelength); + ret = CreateProperty("Wavelength", "546.0", MM::Float, false, pAct); + if (ret != DEVICE_OK) + return ret; + SetPropertyLimits("Wavelength", 425., 700.); + + // Delay + pAct = new CPropertyAction(this, &MeadowlarkLC::OnDelay); + ret = CreateProperty("Device Delay (ms.)", "200.0", MM::Float, false, pAct); + if (ret != DEVICE_OK) + return ret; + SetPropertyLimits("Device Delay (ms.)", 0.0, 200.0); + + // Temparature + pAct = new CPropertyAction(this, &MeadowlarkLC::OnTemperature); + ret = CreateProperty("Temperature (C)", "230.0", MM::Float, true, pAct); + if (ret != DEVICE_OK) + return ret; + //SetPropertyLimits("Temperature", 0., 273.); + + // Active LC number + pAct = new CPropertyAction(this, &MeadowlarkLC::OnNumActiveLCs); + ret = CreateProperty("Active LCs", "0", MM::Integer, true, pAct); + if (ret != DEVICE_OK) + return ret; + + // Total LC number + pAct = new CPropertyAction(this, &MeadowlarkLC::OnNumTotalLCs); + ret = CreateProperty("Total LCs", "0", MM::Integer, true, pAct); + if (ret != DEVICE_OK) + return ret; + + // TNE Duration + pAct = new CPropertyAction(this, &MeadowlarkLC::OnTneDuaration); + ret = CreateProperty("TNE Duration (ms)", IntToString(tneDuration_).c_str(), MM::Integer, false, pAct); + SetPropertyLimits("TNE Duration (ms)", 0, 255); + SetProperty("TNE Duration (ms)", "0"); + if (ret != DEVICE_OK) + return ret; + + // TNE Amplitude + pAct = new CPropertyAction(this, &MeadowlarkLC::OnTneAmplitude); + ret = CreateProperty("TNE Amplitude (V)", IntToString(tneAmplitude_).c_str(), MM::Float, false, pAct); + + SetPropertyLimits("TNE Amplitude (V)", 0.0, tneAmplitude_); + //SetProperty("TNE Amplitude (V)", DoubleToString(tneAmplitude_).c_str()); + + if (ret != DEVICE_OK) + return ret; + + CPropertyActionEx* pActX = 0; + // create an extended (i.e. array) properties 0 through 1 + + // Voltage controls + for (long i = 0; i < numActiveLCs_; ++i) { + ostringstream s; + s << "Voltage (mV) LC-" << char(65 + i); + pActX = new CPropertyActionEx(this, &MeadowlarkLC::OnVoltage, i); + CreateProperty(s.str().c_str(), "7500", MM::Integer, true, pActX); + + if (controllerType_ == g_ControllerDeviceType10V) { + SetPropertyLimits(s.str().c_str(), 0, 10000); + } + else { + SetPropertyLimits(s.str().c_str(), 0, 20000); + } + } + + // Retardance controls -- after Voltage controls + for (long i = 0; i < numActiveLCs_; ++i) { + ostringstream s; + s << "Retardance LC-" << char(65 + i) << " [in waves]"; + pActX = new CPropertyActionEx(this, &MeadowlarkLC::OnRetardance, i); + CreateProperty(s.str().c_str(), "0.5", MM::Float, false, pActX); + SetPropertyLimits(s.str().c_str(), g_ControllerDeviceRetardanceLowLimit, g_ControllerDeviceRetardanceHighLimit); + } + + // Absolute Retardance controls -- after Voltage controls + for (long i = 0; i < numActiveLCs_; ++i) { + ostringstream s; + s << "Retardance LC-" << char(65 + i) << " [in nm.]"; + pActX = new CPropertyActionEx(this, &MeadowlarkLC::OnAbsRetardance, i); + CreateProperty(s.str().c_str(), "100", MM::Float, true, pActX); + } + + // Palettes + for (long i = 0; i < numPalEls_; ++i) { + ostringstream s; + std::string number; + + std::stringstream strstream; + strstream << i; + strstream >> number; + if (i < 10) { + number = "0" + number; + } + + s << "Pal. elem. " << number << "; enter 0 to define; 1 to activate"; + pActX = new CPropertyActionEx(this, &MeadowlarkLC::OnPalEl, i); + CreateProperty(s.str().c_str(), "", MM::String, false, pActX); + } + + pAct = new CPropertyAction(this, &MeadowlarkLC::OnSendToMeadowlarkLC); + ret = CreateProperty("String send to -", "", MM::String, false, pAct); + if (ret != DEVICE_OK) + return ret; + + pAct = new CPropertyAction(this, &MeadowlarkLC::OnGetFromMeadowlarkLC); + ret = CreateProperty("String from -", "", MM::String, true, pAct); + if (ret != DEVICE_OK) + return ret; + + importConfig(); + + // Needed for Busy flag + // changedTime_ = GetCurrentMMTime(); + SetErrorText(99, "Device set busy for "); + + return DEVICE_OK; +} + + +int MeadowlarkLC::Shutdown() +{ + USBDRVD_CloseDevice(dev_Handle); + initialized_ = false; + return DEVICE_OK; +} + + + +//////////////// Action Handlers (MeadowlarkLC) ///////////////// + +int MeadowlarkLC::OnNumTotalLCs(MM::PropertyBase* pProp, MM::ActionType eAct) +{ + if (eAct == MM::BeforeGet) + { + pProp->Set(numTotalLCs_); + } + else if (eAct == MM::AfterSet) + { + pProp->Get(numTotalLCs_); + } + return DEVICE_OK; +} + +int MeadowlarkLC::OnNumActiveLCs(MM::PropertyBase* pProp, MM::ActionType eAct) +{ + if (eAct == MM::BeforeGet) + { + pProp->Set(numActiveLCs_); + } + else if (eAct == MM::AfterSet) + { + pProp->Get(numActiveLCs_); + } + return DEVICE_OK; +} + +int MeadowlarkLC::OnNumPalEls(MM::PropertyBase* pProp, MM::ActionType eAct) +{ + if (eAct == MM::BeforeGet) + { + pProp->Set(numPalEls_); + } + else if (eAct == MM::AfterSet) + { + pProp->Get(numPalEls_); + } + + return DEVICE_OK; +} + +int MeadowlarkLC::GetDesc(MM::PropertyBase* pProp, MM::ActionType eAct) +{ + if (eAct == MM::BeforeGet) + { + pProp->Set(description_.c_str()); + } + else if (eAct == MM::AfterSet) + { + pProp->Get(description_); + } + return DEVICE_OK; +} + +int MeadowlarkLC::OnNumDevices(MM::PropertyBase* pProp, MM::ActionType eAct) +{ + std::string temp; + temp = IntToString(cur_dev); + + if (eAct == MM::BeforeGet) + { + pProp->Set(temp.c_str()); + } + else if (eAct == MM::AfterSet) + { + pProp->Get(temp); + } + + + if (temp == g_Nonedetected) { + cur_dev = 0; + } + else { + cur_dev = StringToInt(temp); + } + + if (description_ == "Not found") { + temp = g_Nonedetected; + pProp->Set(temp.c_str()); + } + + return DEVICE_OK; +} + +int MeadowlarkLC::OnTneDuaration(MM::PropertyBase* pProp, MM::ActionType eAct) +{ + if (eAct == MM::BeforeGet) + { + + BYTE query_volt[] = { 't', 'n', 'e' , ':', char(49), ',', '?', '\r' }; + BYTE statusRead[64]; + + USBDRVD_BulkWrite(dev_Handle, 1, query_volt, sizeof(query_volt)); /* send ld:n,? command */ + + USBDRVD_BulkRead(dev_Handle, 0, statusRead, sizeof(statusRead)); /* read status response */ + + std::string ans = ((char*)statusRead); + + size_t length; + char buffer[64]; + int chN = 9; + for (int j = 7; j < 10; j++) { + if (ans[j] == ',') { + chN = j; + } + } + + length = ans.copy(buffer, chN - 6, 6); + buffer[length] = '\n'; + + int tneP = StringToInt(buffer); + + if (tneP >= 0 && tneP < 256) { + tneDuration_ = tneP; + } + + int sizeC = ans.length(); + size_t length2; + char buffer2[64]; + int chN2 = 9; + for (int j2 = 7; j2 < 11; j2++) { + if (ans[j2] == ',') { + chN2 = j2 + 1; + } + } + + length2 = ans.copy(buffer2, sizeC - chN2, chN2); + buffer2[length2] = '\n'; + + int tneA = StringToInt(buffer2); + + if (tneA >= 0 && tneA <= 65535) { + tneAmplitude_ = roundN(tneA / g_ControllerDeviceTypeVFac, 2); + } + + pProp->Set(tneDuration_); + } + else if (eAct == MM::AfterSet) + { + pProp->Get(tneDuration_); + + int amp = roundN(tneAmplitude_ * g_ControllerDeviceTypeVFac, 1); + + SetTneToDevice(amp, tneDuration_); + } + return DEVICE_OK; +} + +int MeadowlarkLC::OnTneAmplitude(MM::PropertyBase* pProp, MM::ActionType eAct) +{ + if (initialized_) { + if (eAct == MM::BeforeGet) + { + + BYTE query_volt[] = { 't', 'n', 'e' , ':', char(49), ',', '?', '\r' }; + BYTE statusRead[64]; + + USBDRVD_BulkWrite(dev_Handle, 1, query_volt, sizeof(query_volt)); /* send ld:n,? command */ + + USBDRVD_BulkRead(dev_Handle, 0, statusRead, sizeof(statusRead)); /* read status response */ + + std::string ans = ((char*)statusRead); + + size_t length; + char buffer[64]; + int chN = 9; + for (int j = 7; j < 10; j++) { + if (ans[j] == ',') { + chN = j; + } + } + + length = ans.copy(buffer, chN - 6, 6); + buffer[length] = '\n'; + + int tneP = StringToInt(buffer); + + if (tneP >= 0 && tneP < 256) { + tneDuration_ = tneP; + } + + int sizeC = ans.length(); + size_t length2; + char buffer2[64]; + int chN2 = 9; + for (int j2 = 7; j2 < 11; j2++) { + if (ans[j2] == ',') { + chN2 = j2 + 1; + } + } + + length2 = ans.copy(buffer2, sizeC - chN2, chN2); + buffer2[length2] = '\n'; + + int tneA = StringToInt(buffer2); + + if (tneA >= 0 && tneA <= 65535) { + tneAmplitude_ = roundN(tneA / g_ControllerDeviceTypeVFac, 2); + } + + pProp->Set(tneAmplitude_); + } + else if (eAct == MM::AfterSet) + { + pProp->Get(valTNE); + + tneAmplitude_ = valTNE * g_ControllerDeviceTypeVFac; + + SetTneToDevice(tneAmplitude_, tneDuration_); + } + } + return DEVICE_OK; +} + +int MeadowlarkLC::OnRetardance(MM::PropertyBase* pProp, MM::ActionType eAct, long index) +{ + if (eAct == MM::BeforeGet) + { + + if (index + 1 > 0) { + pProp->Set(retardance_[index]); + } + else { + return DEVICE_INVALID_PROPERTY_VALUE; + } + } + else if (eAct == MM::AfterSet) + { + double retardance = retardance_[index]; + double retardanceT; + // read value from property + pProp->Get(retardanceT); + + boolean retLimitCheck = false; + boolean voltLimitCheck = false; + + if (retardanceT * wavelength_ >= g_ControllerDeviceRetardanceAbsRetLow && retardanceT * wavelength_ <= g_ControllerDeviceRetardanceAbsRetHigh) { + retLimitCheck = true; + } + + // write retardance out to device.... + + retardanceT = ceilf(retardanceT * 10000) / 10000; + double voltage = round(RetardanceToVoltage(retardanceT, index)); + + if (controllerType_ == g_ControllerDeviceType10V) { + if (voltage >= 0 && voltage <= 10000) { + voltLimitCheck = true; + } + } + else { + if (voltage >= 0 && voltage <= 20000) { + voltLimitCheck = true; + } + } + + if (retLimitCheck && voltLimitCheck) { + retardance = retardanceT; + } + + retardance_[index] = retardance; + + if (voltage < 0 || voltage > 20000) { + retardance_[index] = VoltageToRetardance(voltage, index); + } + if (voltage < 0) { + voltage = 0; + } + else if (controllerType_ == g_ControllerDeviceType10V) { + if (voltage > 10000) { + voltage = 10000; + } + } + else { + if (voltage > 20000) { + voltage = 20000; + } + } + + if (voltage_[index] == voltage) { + return DEVICE_OK; + } + + // write voltage out to device.... + //ostringstream s; + //s << "Voltage (mV) LC-" << char(65+index); + //std::string s2 = DoubleToString(voltage); + //SetProperty(s.str().c_str(), s2.c_str()); + int volt16bit = static_cast(voltage); + SendVoltageToDevice(volt16bit, index); + voltage_[index] = voltage; + + // changedTime_ = GetCurrentMMTime(); + } + return DEVICE_OK; +} + +int MeadowlarkLC::OnAbsRetardance(MM::PropertyBase* pProp, MM::ActionType eAct, long index) +{ + if (eAct == MM::BeforeGet) + { + if (index + 1 > 0) { + pProp->Set(retardance_[index] * wavelength_); + } + else { + return DEVICE_INVALID_PROPERTY_VALUE; + } + } + else if (eAct == MM::AfterSet) + { + + } + return DEVICE_OK; +} + +int MeadowlarkLC::OnVoltage(MM::PropertyBase* pProp, MM::ActionType eAct, long index) { + + if (initialized_) { + if (eAct == MM::BeforeGet) + { + + BYTE query_volt[] = { 'l', 'd', ':', char(index + 49), ',', '?', '\r' }; + BYTE statusRead[64]; + + USBDRVD_BulkWrite(dev_Handle, 1, query_volt, sizeof(query_volt)); /* send ld:n,? command */ + + USBDRVD_BulkRead(dev_Handle, 0, statusRead, sizeof(statusRead)); /* read status response */ + + std::string ans = ((char*)statusRead); + + size_t length; + char buffer[64]; + length = ans.copy(buffer, 5, 5); + buffer[length] = '\n'; + + //int voltInt = StringToInt(buffer) * 1000/g_ControllerDeviceTypeVFac; + + double voltage = round(StringToInt(buffer) * 1000 / g_ControllerDeviceTypeVFac); + + double maxV = 10000; + if (controllerType_ == g_ControllerDeviceType20V_D3060HV || controllerType_ == g_ControllerDeviceType20V_D5020) { + maxV = 20000; + } + + if (index + 1 >= 0 && voltage > 0 && voltage <= maxV) { + + pProp->Set(voltage); + + if (voltage_[index] == voltage) { + return DEVICE_OK; + } + voltage_[index] = voltage; + + double Retardance = VoltageToRetardance(voltage, index); + retardance_[index] = Retardance; + ostringstream s; + s << "Retardance LC-" << char(65 + index) << " [in waves]"; + std::string s2 = DoubleToString(Retardance); + SetProperty(s.str().c_str(), s2.c_str()); + + } + else { + // return DEVICE_INVALID_PROPERTY_VALUE; + } + } + else if (eAct == MM::AfterSet) + { + double voltage; + + // read value from property + pProp->Get(voltage); + + if (voltage_[index] == voltage) { + return DEVICE_OK; + } + + // double Retardance = VoltageToRetardance(voltage); + // retardance_[index] = Retardance; + // write voltage out to device.... + + double v = ((voltage / 1000) * g_ControllerDeviceTypeVFac); + int volt16bit = static_cast(v); + + SendVoltageToDevice(volt16bit, index); + } + } + return DEVICE_OK; +} + + +int MeadowlarkLC::OnWavelength(MM::PropertyBase* pProp, MM::ActionType eAct) +{ + if (eAct == MM::BeforeGet) + { + //pProp->Set(wavelength_); + //ArrayLcVoltagesRetCurve[4][0] = wavelength_; + } + else if (eAct == MM::AfterSet) + { + double wavelength; + // read value from property + pProp->Get(wavelength); + // write wavelength out to device.... + + wavelength_ = wavelength; + //ArrayLcVoltagesRetCurve[4][1] = wavelength_; + } + generateCurve(); + return DEVICE_OK; +} + +int MeadowlarkLC::OnDelay(MM::PropertyBase* pProp, MM::ActionType eAct) +{ + if (eAct == MM::BeforeGet) + { + double delayT = GetDelayMs(); + delay = delayT * 1000; + pProp->Set(delayT); + } + else if (eAct == MM::AfterSet) + { + double delayT; + pProp->Get(delayT); + delay = delayT * 1000; + SetDelayMs(delayT); + } + + return DEVICE_OK; +} + +int MeadowlarkLC::OnSerialNumber(MM::PropertyBase* pProp, MM::ActionType eAct) +{ + if (eAct == MM::BeforeGet) + { + pProp->Set(serialnum_.c_str()); + } + else if (eAct == MM::AfterSet) + { + pProp->Get(serialnum_); + } + return DEVICE_OK; +} + +int MeadowlarkLC::OnDevAdapterSerialNumber(MM::PropertyBase* pProp, MM::ActionType eAct) +{ + if (eAct == MM::BeforeGet) + { + pProp->Set(g_Dev_Adapter_Ver); + } + return DEVICE_OK; +} + +int MeadowlarkLC::OnActivationKey(MM::PropertyBase* pProp, MM::ActionType eAct) +{ + if (eAct == MM::BeforeGet) + { + pProp->Set(activationKey_.c_str()); + } + else if (eAct == MM::AfterSet) + { + pProp->Get(activationKey_); + } + return DEVICE_OK; +} + +int MeadowlarkLC::OnControllerType(MM::PropertyBase* pProp, MM::ActionType eAct) +{ + if (eAct == MM::BeforeGet) + { + pProp->Set(controllerType_.c_str()); + } + else if (eAct == MM::AfterSet) + { + pProp->Get(controllerType_); + + if (controllerType_ == g_ControllerDeviceType20V_D5020) { + numTotalLCs_ = 2; + } + else { + numTotalLCs_ = 4; + } + SetProperty(g_ControllerTotalLCs, IntToString(numTotalLCs_).c_str()); + } + return DEVICE_OK; +} + +int MeadowlarkLC::OnControllerLCType(MM::PropertyBase* pProp, MM::ActionType eAct) +{ + if (eAct == MM::BeforeGet) + { + pProp->Set(controllerLCType_.c_str()); + controllerLcTypeChange(); + } + else if (eAct == MM::AfterSet) + { + pProp->Get(controllerLCType_); + } + return DEVICE_OK; +} + +int MeadowlarkLC::OnTemperature(MM::PropertyBase* pProp, MM::ActionType eAct) +{ + if (initialized_ == true) { + if (eAct == MM::BeforeGet) + { + + BYTE query_tmp[] = { 't', 'm', 'p', ':', '?', '\n' }; + BYTE status[64]; + + USBDRVD_BulkWrite(dev_Handle, 1, query_tmp, sizeof(query_tmp)); /* send tmp:?, command */ + USBDRVD_BulkRead(dev_Handle, 0, status, sizeof(status)); /* read status response */ + + std::string ans = ((char*)status); + + size_t length; + char buffer[64]; + length = ans.copy(buffer, 5, 4); + buffer[length] = '\0'; + + int tempInt = StringToInt(buffer); + double ret = (tempInt * 500 / 65535) - 273.15; + + pProp->Set(ret); + } + else if (eAct == MM::AfterSet) + { + double temp; + // read value from property + + pProp->Get(temp); + + int tempInt = (temp * 273.15) * (16384 / 500); + + std::string tempStr = (string("tsp:") + IntToString(tempInt)); + + std::vector query_voltc(tempStr.begin(), tempStr.end()); + // write temp out to device.... + + BYTE status[64]; + BYTE query_tmp[sizeof(query_voltc)]; + + int ii = 0; + for (int i = 0; i < sizeof(query_voltc); i++) { + query_tmp[i] = (char)query_voltc[i]; + ii = i; + } + + query_tmp[ii + 1] = (BYTE)'\n'; + query_tmp[ii + 2] = (BYTE)'\0'; + + USBDRVD_BulkWrite(dev_Handle, 1, query_tmp, sizeof(query_tmp)); /* send tsp:t command */ + + USBDRVD_BulkRead(dev_Handle, 0, status, sizeof(status)); /* read status response */ + std::string ans = ((char*)status); + + temperature_ = temp; + } + } + return DEVICE_OK; +} + +int MeadowlarkLC::OnPalEl(MM::PropertyBase* pProp, MM::ActionType eAct, long index) +{ + if (eAct == MM::BeforeGet) + { + pProp->Set(palEl_[index].c_str()); + } + else if (eAct == MM::AfterSet) + { + long setPalEl = 0; + pProp->Get(setPalEl); + + if (setPalEl == 0) { + string str = ""; + for (int i2 = 0; i2 < numActiveLCs_; i2++) { + str = str + " " + DoubleToString(retardance_[i2]); + } + palEl_[index] = DoubleToString(wavelength_) + str; + + for (int i2 = 0; i2 < numActiveLCs_; i2++) { + palette_[index][i2] = retardance_[i2]; + } + + } + else { + for (int i2 = 0; i2 < numActiveLCs_; i2++) { + ostringstream s0; + s0 << "Retardance LC-" << char(65 + i2) << " [in waves]"; + std::string s02 = DoubleToString(palette_[index][i2]); + SetProperty(s0.str().c_str(), s02.c_str()); + } + } + } + return DEVICE_OK; +} + +int MeadowlarkLC::OnSendToMeadowlarkLC(MM::PropertyBase* pProp, MM::ActionType eAct) +{ + + if (eAct == MM::BeforeGet) + { + // pProp->Set(sendToMeadowlarkLC_.c_str()); + } + else if (eAct == MM::AfterSet) + { + // read value from property + pProp->Get(sendToMeadowlarkLC_); + // write retardance out to device.... + int len = strlen(sendToMeadowlarkLC_.c_str()); + char state[6]; + char p[2]; + + std::string propstring = "String from -"; + bool searchQuestionMark = false; + for (int q = 0; q < len; q++) { + if (sendToMeadowlarkLC_[q] == 63) { + searchQuestionMark = true; + } + } + + if (len > 5) { + strncpy(state, sendToMeadowlarkLC_.c_str(), 5); + state[5] = '\0'; + } + + strncpy(p, sendToMeadowlarkLC_.c_str(), 1); + p[1] = '\0'; + + + if (!searchQuestionMark && ((std::string)state == "State" || (std::string)state == "state") && len < 8) { + + int index = 0; + int number = 0; + if (len == 6) { + number = (sendToMeadowlarkLC_[5] - 48); + index = number; + } + else { + number = (sendToMeadowlarkLC_[5] - 48) * 10; + index = number + (sendToMeadowlarkLC_[6] - 48) * 1; + } + + string pre = ""; + if (index < 10) { + pre = "0"; + } + + //changedTime_ = GetCurrentMMTime(); + + ostringstream s0; + s0 << "Pal. elem. " << pre << index << "; enter 0 to define; 1 to activate"; + + SetProperty(s0.str().c_str(), "1"); + + getFromMeadowlarkLC_ = sendToMeadowlarkLC_; + SetProperty(propstring.c_str(), sendToMeadowlarkLC_.c_str()); + + } + else if (!searchQuestionMark && ((std::string)p == "P" || (std::string)p == "p") && len < 4) { + + int index = 0; + int number = 0; + if (len == 2) { + number = (sendToMeadowlarkLC_[1] - 48); + index = number; + } + else { + number = (sendToMeadowlarkLC_[1] - 48) * 10; + index = number + (sendToMeadowlarkLC_[2] - 48) * 1; + } + + string pre = ""; + if (index < 10) { + pre = "0"; + } + + //changedTime_ = GetCurrentMMTime(); + + ostringstream s0; + s0 << "Pal. elem. " << pre << index << "; enter 0 to define; 1 to activate"; + + SetProperty(s0.str().c_str(), "1"); + + getFromMeadowlarkLC_ = sendToMeadowlarkLC_; + SetProperty(propstring.c_str(), sendToMeadowlarkLC_.c_str()); + + } + else if (!searchQuestionMark && ((std::string)p == "E" || (std::string)p == "e") && len < 4) { + + int numCycles = 0; + int number = 0; + if (len == 2) { + number = (sendToMeadowlarkLC_[1] - 48); + numCycles = number * 1; + } + else if (len == 3 && sendToMeadowlarkLC_[1] == ' ') { + number = (sendToMeadowlarkLC_[2] - 48); + numCycles = number * 1; + } + else { + number = (sendToMeadowlarkLC_[1] - 48) * 10; + numCycles = number + (sendToMeadowlarkLC_[2] - 48); + } + + doExercise(numCycles * 10); + + //changedTime_ = GetCurrentMMTime(); + + ostringstream sss; sss << "Excercising for " << number << " cycles please wait."; + SetProperty(propstring.c_str(), sss.str().c_str()); + + double oldVals[10]; + for (int i2 = 0; i2 < numActiveLCs_; i2++) { + oldVals[i2] = retardance_[i2]; + } + + if ((sendToMeadowlarkLC_ != "R1" || sendToMeadowlarkLC_ != "R 1" || sendToMeadowlarkLC_ != "r1" || sendToMeadowlarkLC_ != "r 1")) { + + interruptExercise_ = true; + + for (int i2 = 0; i2 < numActiveLCs_; i2++) { + ostringstream s0; + s0 << "Retardance LC-" << char(65 + i2) << " [in waves]"; + SetProperty(s0.str().c_str(), "0.5"); + } + Sleep(100); + for (int i2 = 0; i2 < numActiveLCs_; i2++) { + ostringstream s0; + s0 << "Retardance LC-" << char(65 + i2) << " [in waves]"; + SetProperty(s0.str().c_str(), "1.5"); + } + CDeviceUtils::SleepMs(100); + + interruptExercise_ = false; + } + + for (int i2 = 0; i2 < numActiveLCs_; i2++) { + ostringstream s0; + s0 << "Retardance LC-" << char(65 + i2) << " [in waves]"; + SetProperty(s0.str().c_str(), DoubleToString(oldVals[i2]).c_str()); + } + + getFromMeadowlarkLC_ = sendToMeadowlarkLC_; + SetProperty(propstring.c_str(), sendToMeadowlarkLC_.c_str()); + + } + else if ((sendToMeadowlarkLC_ == "R?" || sendToMeadowlarkLC_ == "R ?" || sendToMeadowlarkLC_ == "r?" || sendToMeadowlarkLC_ == "r ?")) { + + sendToMeadowlarkLC_ = "R0"; + getFromMeadowlarkLC_ = sendToMeadowlarkLC_; + SetProperty(propstring.c_str(), sendToMeadowlarkLC_.c_str()); + + } + else if (!searchQuestionMark && ((std::string)p == "L" || (std::string)p == "l")) { + + std::string myStr = "L " + sendToMeadowlarkLC_.substr(1, len); + vector numbers = getNumbersFromMessage(myStr, briefModeQ_); + //changedTime_ = GetCurrentMMTime(); + + for (int i2 = 0; i2 < numActiveLCs_; i2++) { + ostringstream s0; + s0 << "Retardance LC-" << char(65 + i2) << " [in waves]"; + SetProperty(s0.str().c_str(), DoubleToString(numbers[i2]).c_str()); + } + + getFromMeadowlarkLC_ = sendToMeadowlarkLC_; + SetProperty(propstring.c_str(), sendToMeadowlarkLC_.c_str()); + + } + else if (!searchQuestionMark && ((std::string)p == "D" || (std::string)p == "d") && len < 4) { + + int index = 0; + int number = 0; + if (len == 2) { + number = (sendToMeadowlarkLC_[1] - 48); + index = number; + } + else { + number = (sendToMeadowlarkLC_[1] - 48) * 10; + index = number + (sendToMeadowlarkLC_[2] - 48) * 1; + } + + string pre = ""; + if (index < 10) { + pre = "0"; + } + + //changedTime_ = GetCurrentMMTime(); + + ostringstream s0; + s0 << "Pal. elem. " << pre << index << "; enter 0 to define; 1 to activate"; + + SetProperty(s0.str().c_str(), "0"); + + getFromMeadowlarkLC_ = sendToMeadowlarkLC_; + SetProperty(propstring.c_str(), sendToMeadowlarkLC_.c_str()); + + } + else if (!searchQuestionMark && len == 5 && ((sendToMeadowlarkLC_.substr(0, 2) == "SP") || (sendToMeadowlarkLC_.substr(0, 2) == "sp"))) { + + int w = StringToInt(sendToMeadowlarkLC_.substr(2)); + + for (int i = 0; i < 250; i++) + { + if (ConfigData[i][0] == w) { + // Palettes + SetProperty("Wavelength", DoubleToString(ConfigData[i][0]).c_str()); + + for (long i = 0; i < numPalEls_; ++i) { + ostringstream s; + std::string number; + + std::stringstream strstream; + strstream << i; + strstream >> number; + if (i < 10) { + number = "0" + number; + } + + for (int i2 = 0; i2 < numActiveLCs_; i2++) { + ostringstream s0; + s0 << "Retardance LC-" << char(65 + i2) << " [in waves]"; + SetProperty(s0.str().c_str(), DoubleToString(ConfigData[i][i2 + 1]).c_str()); + } + + s << "Pal. elem. " << number << "; enter 0 to define; 1 to activate"; + SetProperty(s.str().c_str(), "0"); + } + } + } + + } + else if (!searchQuestionMark && ((std::string)p == "W" || (std::string)p == "w")) { + + std::string myStr = sendToMeadowlarkLC_.substr(1, len).c_str(); + vector numbers = getNumbersFromMessage(myStr, briefModeQ_); + //changedTime_ = GetCurrentMMTime(); + + SetProperty("Wavelength", DoubleToString(numbers[0]).c_str()); + + getFromMeadowlarkLC_ = "W " + sendToMeadowlarkLC_; + SetProperty(propstring.c_str(), sendToMeadowlarkLC_.c_str()); + + } + else if (searchQuestionMark && (sendToMeadowlarkLC_ == "W ?" || sendToMeadowlarkLC_ == "W?" || sendToMeadowlarkLC_ == "w ?" || sendToMeadowlarkLC_ == "w?")) { + + getFromMeadowlarkLC_ = "W " + DoubleToString(wavelength_); + SetProperty(propstring.c_str(), getFromMeadowlarkLC_.c_str()); + + } + else if (searchQuestionMark && (sendToMeadowlarkLC_ == "L ?" || sendToMeadowlarkLC_ == "L?" || sendToMeadowlarkLC_ == "l ?" || sendToMeadowlarkLC_ == "l?")) { + + string str = ""; + for (int i2 = 0; i2 < numActiveLCs_; i2++) { + str = str + " " + DoubleToString(retardance_[i2]); + } + + getFromMeadowlarkLC_ = "L " + str; + SetProperty(propstring.c_str(), getFromMeadowlarkLC_.c_str()); + + } + else if (searchQuestionMark && (sendToMeadowlarkLC_ == "V ?" || sendToMeadowlarkLC_ == "V?" || sendToMeadowlarkLC_ == "v?" || sendToMeadowlarkLC_ == "v?")) { + + getFromMeadowlarkLC_ = description_; + SetProperty(propstring.c_str(), description_.c_str()); + + } + //else if (!searchQuestionMark && ((sendToMeadowlarkLC_ == "About") || sendToMeadowlarkLC_ == "about")) { + + // MessageBox(0, g_About, "About", 0); + // SetProperty(propstring.c_str(), description_.c_str()); + + //} + //else if (!searchQuestionMark && ((sendToMeadowlarkLC_ == "Help") || sendToMeadowlarkLC_ == "help")) { + + // MessageBox(0, g_About, "About", 0); + // SetProperty(propstring.c_str(), description_.c_str()); + + //} + else if (!searchQuestionMark && ((sendToMeadowlarkLC_ == "import") || sendToMeadowlarkLC_ == "IMPORT")) { + + loadDefault(); + import(controllerLCType_Curve); + + } + else if (!searchQuestionMark && ((sendToMeadowlarkLC_ == "export") || sendToMeadowlarkLC_ == "EXPORT")) { + + exportCurve(); + + } + else if (!searchQuestionMark && ((sendToMeadowlarkLC_ == "generate") || sendToMeadowlarkLC_ == "GENERATE")) { + + generateCurve(); + + } + else if (!searchQuestionMark && ((sendToMeadowlarkLC_ == "exportloaded") || sendToMeadowlarkLC_ == "EXPORTLOADED")) { + + exportloadedCurve(); + + } + else if (!searchQuestionMark && ((sendToMeadowlarkLC_ == "importdefault") || sendToMeadowlarkLC_ == "IMPORTDEFAULT")) { + + loadDefault(); + + } + else if (!searchQuestionMark && (sendToMeadowlarkLC_ == "")) { + + SetProperty(propstring.c_str(), ""); + + } + else { + getFromMeadowlarkLC_ = sendToMeadowlarkLC_; + } + } + return DEVICE_OK; +} + +int MeadowlarkLC::OnGetFromMeadowlarkLC(MM::PropertyBase* pProp, MM::ActionType eAct) +{ + if (eAct == MM::BeforeGet) + { + // GetSerialAnswer (port_.c_str(), "\r", getFromMeadowlarkLC_); + pProp->Set(getFromMeadowlarkLC_.c_str()); + } + else if (eAct == MM::AfterSet) + { + + } + return DEVICE_OK; +} + +bool MeadowlarkLC::Busy() +{ + if (delay.getMsec() > 0.0) { + MM::MMTime interval = GetCurrentMMTime() - changedTime_; + if (interval.getMsec() < delay.getMsec()) { + return true; + } + } + + return false; +} + + +std::vector MeadowlarkLC::getNumbersFromMessage(std::string variLCmessage, bool briefMode) { + std::istringstream variStream(variLCmessage); + std::string prefix; + double val; + std::vector values; + + if (!briefMode) { + variStream >> prefix; + } + for (;;) { + variStream >> val; + if (!variStream.fail()) { + values.push_back(val); + } + else { + break; + } + } + + return values; +} + +std::string MeadowlarkLC::IntToString(int N) +{ + ostringstream ss(""); + ss << N; + return ss.str(); +} + +std::string MeadowlarkLC::DoubleToString(double N) +{ + ostringstream ss(""); + ss << N; + return ss.str(); +} + +int MeadowlarkLC::StringToInt(std::string str) +{ + std::istringstream variStream(str); + int val; + + variStream >> val; + + return val; +} + +double MeadowlarkLC::StringToDouble(std::string str) +{ + std::istringstream variStream(str); + double val; + + variStream >> val; + + return val; +} + +std::string MeadowlarkLC::RemoveChars(const std::string& source, const std::string& chars) { + std::string result = ""; + for (unsigned int i = 0; i < source.length(); i++) { + bool foundany = false; + for (unsigned int j = 0; j < chars.length() && !foundany; j++) { + foundany = (source[i] == chars[j]); + } + if (!foundany) { + result += source[i]; + } + } + return result; +} + +void MeadowlarkLC::hexconvert(char* text, unsigned char bytes[]) +{ + int i; + int temp; + + for (i = 0; i < 4; ++i) { + sscanf(text + 2 * i, "%2x", &temp); + bytes[i] = temp; + } +} + +vector intToBytes(int paramInt) +{ + vector arrayOfByte(4); + for (int i = 0; i < 4; i++) + arrayOfByte[3 - i] = (paramInt >> (i * 8)); + return arrayOfByte; +} + +double MeadowlarkLC::round(double number) +{ + return number < 0.0 ? ceil(number - 0.5) : floor(number + 0.5); +} + +double MeadowlarkLC::roundN(double val, int precision) +{ + std::stringstream s; + s << std::setprecision(precision) << std::setiosflags(std::ios_base::fixed) << val; + s >> val; + return val; +} + +double MeadowlarkLC::VoltageToRetardance(double volt, long index) { + + double retardance = 0; + double FacRetardance = 0; + + double myRetardance = 0; + double diff = 0; + + double upper = 0; + double lower = 0; + + for (int i = 0; i < ArrayLength2 - 1; i++) { + + if ((volt > round(ArrayLcVoltagesRetCurve[i][0]) && volt < round(ArrayLcVoltagesRetCurve[i + 1][0]))) { + if (i == 0) { + FacRetardance = 1 - (round(ArrayLcVoltagesRetCurve[0][0]) / volt); + myRetardance = ArrayLcVoltagesRetCurve[0][1 + index] + ((ArrayLcVoltagesRetCurve[0][1 + index] - ArrayLcVoltagesRetCurve[0][1 + index]) * FacRetardance); + break; + } + else if (i == ArrayLength2 - 1) { + FacRetardance = 1 - (round(ArrayLcVoltagesRetCurve[ArrayLength2 - 1][0]) / volt); + diff = ((round(ArrayLcVoltagesRetCurve[ArrayLength2 - 1][0]) - round(ArrayLcVoltagesRetCurve[ArrayLength2 - 2][0])) * FacRetardance); + + myRetardance = ArrayLcVoltagesRetCurve[ArrayLength2 - 2][1 + index] + diff; + break; + } + else { + upper = ArrayLcVoltagesRetCurve[i][1 + index]; + lower = ArrayLcVoltagesRetCurve[i + 1][1 + index]; + + FacRetardance = ArrayLcVoltagesRetCurve[i][0] / volt; + diff = upper - lower; + + double v1 = ArrayLcVoltagesRetCurve[i + 1][0] - volt; + double v2 = volt - ArrayLcVoltagesRetCurve[i][0]; + double totDiff = ArrayLcVoltagesRetCurve[i + 1][0] - ArrayLcVoltagesRetCurve[i][0]; + + if (v1 < v2) { + double fac = v1 / totDiff; + myRetardance = lower + (diff * fac); + retardance = myRetardance / wavelength_; + } + else { + double fac = v2 / totDiff; + myRetardance = upper - (diff * fac); + retardance = myRetardance / wavelength_; + } + return retardance; + } + } + else if (ArrayLcVoltagesRetCurve[i][0] == 20000) { + myRetardance = ArrayLcVoltagesRetCurve[i][1 + index]; + } + } + + retardance = myRetardance / wavelength_; + + return retardance; +} + +double MeadowlarkLC::RetardanceToVoltage(double retard, long index) { + + double voltage = 0; + double FacRetardance = 0; + double diff = 0; + double myAbsRetardance = (wavelength_ * retard); + + double upper = 0; + double lower = 0; + + for (int i = 0; i < ArrayLength2; i++) { + if (myAbsRetardance >= ArrayLcVoltagesRetCurve[i][1 + index]) { + if (i == 0) { + FacRetardance = 1 - (ArrayLcVoltagesRetCurve[0][1 + index] / myAbsRetardance); + voltage = round(ArrayLcVoltagesRetCurve[0][0]) - ((round(ArrayLcVoltagesRetCurve[1][0]) - round(ArrayLcVoltagesRetCurve[0][0])) * FacRetardance); + break; + } + else if (i == ArrayLength2 - 1) { + FacRetardance = 1 - (ArrayLcVoltagesRetCurve[ArrayLength2 - 1][1 + index] / myAbsRetardance); + voltage = round(ArrayLcVoltagesRetCurve[ArrayLength2 - 1][0]) - ((round(ArrayLcVoltagesRetCurve[ArrayLength2 - 1][0]) - round(ArrayLcVoltagesRetCurve[ArrayLength2 - 2][0])) * FacRetardance); + break; + } + else { + lower = ArrayLcVoltagesRetCurve[i][0]; + upper = ArrayLcVoltagesRetCurve[i - 1][0]; + + if (upper == 20000) { + return 20001; // instruct out of range + } + + FacRetardance = myAbsRetardance / ArrayLcVoltagesRetCurve[i][1 + index]; + diff = lower - upper; + + double v1 = ArrayLcVoltagesRetCurve[i - 1][1 + index] - myAbsRetardance; + double v2 = myAbsRetardance - ArrayLcVoltagesRetCurve[i][1 + index]; + double totDiff = ArrayLcVoltagesRetCurve[i - 1][1 + index] - ArrayLcVoltagesRetCurve[i][1 + index]; + + if (v1 > v2) { + double fac = v1 / totDiff; + voltage = upper + (diff * fac); + } + else { + double fac = v2 / totDiff; + voltage = lower - (diff * fac); + } + + break; + } + } + else if (ArrayLcVoltagesRetCurve[i][0] == 20000 && myAbsRetardance < ArrayLcVoltagesRetCurve[i][1 + index]) { + return 20001; // instruct out of range + } + } + + return round(voltage); +} + + +void MeadowlarkLC::SendVoltageToDevice(int volt16bit, long index) { + + if (index + 1 > 0 && volt16bit >= 0 && volt16bit <= 65535) { + + std::string voltStr = IntToString(volt16bit); + std::vector query_voltc(voltStr.begin(), voltStr.end()); + + query_voltc.push_back('\0'); + + // write temp out to device.... + BYTE status[64]; + + BYTE a1 = '\r'; + BYTE a2 = '\r'; + BYTE a3 = '\r'; + BYTE a4 = '\r'; + BYTE a5 = '\r'; + BYTE a6 = '\r'; + + int sizeC = voltStr.length(); + int s = 0; + + switch (sizeC) { + case 5: + a1 = voltStr[0]; + a2 = voltStr[1]; + a3 = voltStr[2]; + a4 = voltStr[3]; + a5 = voltStr[4]; + break; + case 4: + a1 = '0'; + a2 = voltStr[0]; + a3 = voltStr[1]; + a4 = voltStr[2]; + a5 = voltStr[3]; + s = 4; + break; + case 3: + a1 = '0'; + a2 = '0'; + a3 = voltStr[0]; + a4 = voltStr[1]; + a5 = voltStr[2]; + s = 8; + break; + case 2: + a1 = '0'; + a2 = '0'; + a3 = '0'; + a4 = voltStr[0]; + a5 = voltStr[1]; + s = 12; + break; + case 1: + a1 = '0'; + a2 = '0'; + a3 = '0'; + a4 = '0'; + a5 = voltStr[0]; + s = 16; + break; + } + + BYTE test_query_volt[] = { 'l', 'd', ':', char(index + 49), ',' ,char(a1),char(a2),char(a3),char(a4),char(a5),a6 }; + + + USBDRVD_BulkWrite(dev_Handle, 1, test_query_volt, sizeof(test_query_volt)); /* send ld:n,i command */ + + USBDRVD_BulkRead(dev_Handle, 0, status, sizeof(status)); /* read status response */ + + /* output status until a is found */ + + // Needed for Busy flag + changedTime_ = GetCurrentMMTime(); + } +} + +void MeadowlarkLC::SetTneToDevice(int amplitude, double duration) { + + if (tneDuration_ >= 0 && tneDuration_ <= 255) { + + std::string tneStrD = IntToString(duration); + + // write temp out to device.... + BYTE status[64]; + + BYTE a1 = '\r'; + BYTE a2 = '\r'; + BYTE a3 = '\r'; + BYTE a4 = '\r'; + + int sizeC = tneStrD.length(); + + switch (sizeC) { + case 3: + a1 = tneStrD[0]; + a2 = tneStrD[1]; + a3 = tneStrD[2]; + break; + case 2: + a1 = '0'; + a2 = tneStrD[0]; + a3 = tneStrD[1]; + break; + case 1: + a1 = '0'; + a2 = '0'; + a3 = tneStrD[0]; + break; + } + + std::string tneStrA = IntToString(amplitude); + + BYTE b1 = '\r'; + BYTE b2 = '\r'; + BYTE b3 = '\r'; + BYTE b4 = '\r'; + BYTE b5 = '\r'; + + sizeC = tneStrA.length(); + + switch (sizeC) { + case 5: + b1 = tneStrA[0]; + b2 = tneStrA[1]; + b3 = tneStrA[2]; + b4 = tneStrA[3]; + b5 = tneStrA[4]; + break; + case 4: + b1 = '0'; + b2 = tneStrA[0]; + b3 = tneStrA[1]; + b4 = tneStrA[2]; + b5 = tneStrA[3]; + break; + case 3: + b1 = '0'; + b2 = '0'; + b3 = tneStrA[0]; + b4 = tneStrA[1]; + b5 = tneStrA[2]; + break; + case 2: + b1 = '0'; + b2 = '0'; + b3 = '0'; + b4 = tneStrA[0]; + b5 = tneStrA[1]; + break; + case 1: + b1 = '0'; + b2 = '0'; + b3 = '0'; + b4 = '0'; + b5 = tneStrA[0]; + break; + } + + BYTE test_query_tne[] = { 't', 'n', 'e', ':', char(0 + 49), ',' ,char(a1),char(a2),char(a3), ',',char(b1),char(b2),char(b3),char(b4),char(b5), a4 }; + USBDRVD_BulkWrite(dev_Handle, 1, test_query_tne, sizeof(test_query_tne)); /* send ld:n,i command */ + USBDRVD_BulkRead(dev_Handle, 0, status, sizeof(status)); /* read status response */ + + BYTE test_query_tne2[] = { 't', 'n', 'e', ':', char(1 + 49), ',' ,char(a1),char(a2),char(a3), ',',char(b1),char(b2),char(b3),char(b4),char(b5), a4 }; + USBDRVD_BulkWrite(dev_Handle, 1, test_query_tne2, sizeof(test_query_tne2)); /* send ld:n,i command */ + USBDRVD_BulkRead(dev_Handle, 0, status, sizeof(status)); /* read status response */ + + /* output status until a is found */ + + //changedTime_ = GetCurrentMMTime(); + } +} + +void MeadowlarkLC::doExercise(int seconds) { + + + for (int i = 0; i < seconds; i++) { + SendVoltageToDevice(0, 0); + SendVoltageToDevice(0, 1); + + CDeviceUtils::SleepMs(500); + + if (interruptExercise_) { + break; + } + + SendVoltageToDevice(65535, 0); + SendVoltageToDevice(65535, 1); + } + + interruptExercise_ = false; + //changedTime_ = GetCurrentMMTime(); +} + +void MeadowlarkLC::exportCurve() { + ostringstream s; + s << serialnum_ << "_MeadowlarkLcCalib_Export_" << wavelength_ << ".csv"; + ofstream arrayData(s.str()); // File Creation(on C drive) // overwrite + + //Outputs array to txtFile + arrayData << "Volt(mv),LC-A,LC-B" << endl; + arrayData << "-,-,-" << endl; + arrayData << "0," << wavelength_ << "," << wavelength_ << endl; + + for (int i = 0; i < ArrayLength2 - 1; i++) + { + arrayData << ArrayLcVoltagesRetCurve[i][0] << "," << ArrayLcVoltagesRetCurve[i][1] << "," << ArrayLcVoltagesRetCurve[i][2] << endl; //Outputs array to txtFile + } + arrayData << "-,-,-" << endl; + + arrayData.close(); +} + +void MeadowlarkLC::exportConfig() { + ostringstream s; + s << "MeadowlarkLc_" << serialnum_ << "_Config.csv"; + ofstream arrayData(s.str()); // File Creation(on C drive) // overwrite + + //Outputs array to txtFile + arrayData << "Edit or Define new Palettes. 1st is used as default when Micro-Manager loads. Please keep starting/ending delimiters \"-\" intact." << endl; + arrayData << "Wavelength,LC-A,LC-B" << endl; + arrayData << "-,-,-" << endl; + + if (ConfigData[0][0] == 0) { + for (int i = 0; i < 5; i++) + { + arrayData << roundN(ConfigDataDefaults[i][0], 2) << "," << roundN(ConfigDataDefaults[i][1], 2) << "," << roundN(ConfigDataDefaults[i][2], 2) << endl; //Outputs array to txtFile + } + + } + else { + for (int i = 0; i < 250; i++) + { + if (ConfigData[i][0] == 0) { + break; + } + else { + arrayData << ConfigData[i][0] << "," << ConfigData[i][1] << "," << ConfigData[i][2] << endl; //Outputs array to txtFile + } + } + } + + arrayData << "-,-,-" << endl; + + arrayData.close(); +} + +void MeadowlarkLC::exportloadedCurve() { + ostringstream s; + s << serialnum_ << "_MeadowlarkLcCalib_Export_Loaded.csv"; + ofstream arrayData(s.str()); // File Creation(on C drive) // overwrite + + //Outputs array to txtFile + arrayData << "Volt(mv),LC-A,LC-B,Volt(mv),LC-A,LC-B,Volt(mv),LC-A,LC-B" << endl; + arrayData << "-,-,-,-,-,-,-,-,-" << endl; + + for (int r = 0; r < ArrayLength2 - 1; r++) + for (int c = 0; c < numberofCurves; c++) { + { + if (c == 0 && r == 0) { + for (int w = 0; w < numberofCurves; w++) { + if (w == numberofCurves - 1) { + arrayData << Wavelengths[w] << endl; + } + else { + arrayData << Wavelengths[w] << ","; + } + } + } + if (c == numberofCurves - 1) { + arrayData << ArrayLcVoltagesRetLoaded[r][c] << "," << endl; + } + else { + arrayData << ArrayLcVoltagesRetLoaded[r][c] << ","; //Outputs array to txtFile + } + } + } + arrayData << "-,-,-" << endl; + + arrayData.close(); +} + +void MeadowlarkLC::clearConfig() { + + for (int i = 0; i < 250; i++) + { + for (int i2 = 0; i2 < 3; i2++) { + ConfigData[i][i2] == 0; + } + } +} + +void MeadowlarkLC::convertStringtoStringArray(std::string str) { + + stringstream infile(str); + + vector > data; + int c = 0; + bool start = false; + bool end = false; + bool hasDeterminedNumberOfWavelength = false; + + while (infile.good()) + { + + string s; + if (!getline(infile, s)) break; + + if (s[0] == '-' && !start) { + start = true; + } + else if (s[0] == '-' && !end) { + end = true; + } + + if (!hasDeterminedNumberOfWavelength && start && s[0] != '-') { + istringstream ss(s); + vector record; + + int c2 = 0; + while (ss) + { + string s; + if (!getline(ss, s, ',')) break; + record.push_back(s); + Wavelengths[c2] = StringToDouble(s); + c2++; + } + + numberofCurves = (c2) / 3; // 3 columns used by each curve + hasDeterminedNumberOfWavelength = true; + + } + else if (start && hasDeterminedNumberOfWavelength && !end) { + istringstream ss(s); + vector record; + + int c2 = 0; + while (ss) + { + string s; + if (!getline(ss, s, ',')) break; + record.push_back(s); + ArrayLcVoltagesRetLoaded[c][c2] = StringToDouble(s); + c2++; + } + + data.push_back(record); + c++; + + ArrayLength2 = c + 1; + } + + generateCurve(); + } + + if (!infile.eof()) + { + cerr << "End of Line!\n"; + } +} + +void MeadowlarkLC::import(std::string calibCurveFilename) { + + if (!checkCalibFile(calibCurveFilename)) { // check file exists and is valid // ToDo: Better check conditions + return; + } + + vector > data; + ifstream infile(calibCurveFilename); + int c = 0; + bool start = false; + bool end = false; + bool hasDeterminedNumberOfWavelength = false; + + while (infile) + { + + string s; + if (!getline(infile, s)) break; + + if (s[0] == '-' && !start) { + start = true; + } + else if (s[0] == '-' && !end) { + end = true; + } + + if (!hasDeterminedNumberOfWavelength && start && s[0] != '-') { + istringstream ss(s); + vector record; + + int c2 = 0; + while (ss) + { + string s; + if (!getline(ss, s, ',')) break; + record.push_back(s); + Wavelengths[c2] = StringToDouble(s); + c2++; + } + + numberofCurves = (c2) / 3; // 3 columns used by each curve + hasDeterminedNumberOfWavelength = true; + + } + else if (start && hasDeterminedNumberOfWavelength && !end) { + istringstream ss(s); + vector record; + + int c2 = 0; + while (ss) + { + string s; + if (!getline(ss, s, ',')) break; + record.push_back(s); + ArrayLcVoltagesRetLoaded[c][c2] = StringToDouble(s); + c2++; + } + + data.push_back(record); + c++; + + ArrayLength2 = c + 1; + } + + generateCurve(); + } + + if (!infile.eof()) + { + cerr << "End of Line!\n"; + } +} + +void MeadowlarkLC::importConfig() { + + ostringstream s; + s << "MeadowlarkLc_" << serialnum_ << "_Config.csv"; + string configFilename = s.str(); + + if (!checkConfigFile(configFilename)) { // check file exists and is valid + exportConfig(); + return; + } + + clearConfig(); + + vector > data; + ifstream infile(configFilename); + int c = 0; + bool start = false; + bool end = false; + bool skip = true; + + while (infile) + { + + string s; + if (!getline(infile, s)) break; + + if (s[0] == '-' && !start) { + start = true; skip = true; + } + else if (s[0] == '-' && !end) { + end = true; skip = true; + } + else { + skip = false; + } + + if (start && !end && !skip) { + istringstream ss(s); + vector record; + + int c2 = 0; + while (ss) + { + string s; + if (!getline(ss, s, ',')) break; + record.push_back(s); + ConfigData[c][c2] = StringToDouble(s); + c2++; + } + + data.push_back(record); + c++; + } + } + + if (!infile.eof()) + { + cerr << "End of Line!\n"; + } + + // Palettes + for (long i = 0; i < numPalEls_; ++i) { + ostringstream s; + std::string number; + + std::stringstream strstream; + strstream << i; + strstream >> number; + if (i < 10) { + number = "0" + number; + } + + SetProperty("Wavelength", DoubleToString(ConfigData[i][0]).c_str()); + + for (int i2 = 0; i2 < numActiveLCs_; i2++) { + ostringstream s0; + s0 << "Retardance LC-" << char(65 + i2) << " [in waves]"; + SetProperty(s0.str().c_str(), DoubleToString(ConfigData[i][i2 + 1]).c_str()); + } + + s << "Pal. elem. " << number << "; enter 0 to define; 1 to activate"; + SetProperty(s.str().c_str(), "0"); + } +} + +bool MeadowlarkLC::checkCalibFile(std::string calibCurveFilename) { + vector > data; + ifstream infile(calibCurveFilename); + + if (!infile) { + controllerLCType_ = g_ControllerLCType_Internal; + return false; + } + + string s0; + if (!getline(infile, s0)); + if ((s0[0] != 'V' || s0[s0.length() - 1] != 'B') && (s0[0] != 'L')) { // starting line of calib file has words Voltage and ends with 'B' + controllerLCType_ = g_ControllerLCType_Internal; + return false; + } + + string s; int c = 0; + while (infile) { + if (!getline(infile, s)) { + break; + } + else { + c++; + s0 = s; + }; + } + if (s0[0] != '-' || s0[s0.length() - 1] != '-') { // EOF has '-' + controllerLCType_ = g_ControllerLCType_Internal; + return false; + } + if (c < 100) { // calibration file is expected to have more than 100 voltage points (Meadowlark provides files with min. 197 points) + controllerLCType_ = g_ControllerLCType_Internal; + return false; + } + + return true; +} + +bool MeadowlarkLC::checkConfigFile(std::string configFilename) { + vector > data; + ifstream infile(configFilename); + + string s; int c = 0; + while (infile) { + if (!getline(infile, s)) { + break; + } + else { + c++; + }; + } + + if (c < 4) { + return false; + } + + return true; +} + +void MeadowlarkLC::controllerLcTypeChange() { + // Add multiple curves switch and load from resource ID + // + if (controllerLCType_ == g_ControllerLCType_B001) { + controllerLCType_Curve = g_ControllerLCType_B001; + loadResource(IDR_TEXT1); + convertStringtoStringArray(lcCurve_); + } + else if (controllerLCType_ == g_ControllerLCType_B002) { + controllerLCType_Curve = g_ControllerLCType_B002; + loadResource(IDR_TEXT2); + convertStringtoStringArray(lcCurve_); + } + else if (controllerLCType_ == g_ControllerLCType_B14181) { + controllerLCType_Curve = g_ControllerLCType_B14181_Curves; + loadResource(IDR_B14181); + convertStringtoStringArray(lcCurve_); + } + else if (controllerLCType_ == g_ControllerLCType_B14182) { + controllerLCType_Curve = g_ControllerLCType_B14182_Curves; + loadResource(IDR_B14182); + convertStringtoStringArray(lcCurve_); + } + else if (controllerLCType_ == g_ControllerLCType_B14183) { + controllerLCType_Curve = g_ControllerLCType_B14183_Curves; + loadResource(IDR_B14183); + convertStringtoStringArray(lcCurve_); + } + else if (controllerLCType_ == g_ControllerLCType_T001) { + controllerLCType_Curve = g_ControllerLCType_T001_Curves; + loadResource(IDR_T001); + convertStringtoStringArray(lcCurve_); + } + else if (controllerLCType_ == g_ControllerLCType_F001 || controllerLCType_ == g_ControllerLCType_F001b) { + controllerLCType_Curve = g_ControllerLCType_F001_Curves; + loadDefault(); + import(controllerLCType_Curve); + } + else if (controllerLCType_ == g_ControllerLCType_F002) { + controllerLCType_Curve = serialnum_ + g_ControllerLCType_F002_Curves; + loadDefault(); + import(controllerLCType_Curve); + } + else if (controllerLCType_ == g_ControllerLCType_Internal) { + loadDefault(); + } + generateCurve(); +} + +void MeadowlarkLC::generateCurve() { + + int curve = 1; boolean lowerThanCurve = false; boolean higherThanCurve = false; boolean isCurve = false; int maxCurves = (numberofCurves * 3) - 1; + + if (numberofCurves == 1) { + for (int i = 0; i < ArrayLength2; i++) { + ArrayLcVoltagesRetCurve[i][0] = ArrayLcVoltagesRetLoaded[i][0]; + ArrayLcVoltagesRetCurve[i][1] = ArrayLcVoltagesRetLoaded[i][1]; + ArrayLcVoltagesRetCurve[i][2] = ArrayLcVoltagesRetLoaded[i][2]; + } + } + else { + for (int c = 0; c < (numberofCurves * 3); c++) { + if ((int)wavelength_ == (int)Wavelengths[c + 1]) { + isCurve = true; curve = c; break; + } + else if (c > 0 && (int)wavelength_ > (int)Wavelengths[c - 1] && (int)wavelength_ < (int)Wavelengths[c + 1] && c < (numberofCurves * 3)) { // within + curve = c; break; + } + else if ((int)wavelength_ < (int)Wavelengths[1]) { // below lowest + curve = c; lowerThanCurve = true; break; + } + else if ((int)wavelength_ > (int)Wavelengths[maxCurves]) { // above highest + curve = maxCurves - 2; higherThanCurve = true; break; + } + } + + if (lowerThanCurve) { + double w_diff = Wavelengths[curve + 1] - wavelength_; + double new_wavelength = Wavelengths[curve + 1] + w_diff; + double fact1 = (Wavelengths[4] - new_wavelength) / (Wavelengths[4] - Wavelengths[2]); + double fact2 = (new_wavelength - Wavelengths[2]) / (Wavelengths[4] - Wavelengths[2]); + + for (int i = 0; i < ArrayLength2; i++) { + double val = ArrayLcVoltagesRetLoaded[i][curve]; + ArrayLcVoltagesRetCurve[i][0] = val; + double curve1aVal = getValueFromArray(val, 1, 0); + double curve1bVal = getValueFromArray(val, 2, 0); + double curve2aVal = getValueFromArray(val, 4, 3); + double curve2bVal = getValueFromArray(val, 5, 3); + ArrayLcVoltagesRetCurve[i][1] = 2 * curve1aVal - ((curve1aVal * fact1) + (curve2aVal * fact2)); + ArrayLcVoltagesRetCurve[i][2] = 2 * curve1bVal - ((curve1bVal * fact1) + (curve2bVal * fact2)); + } + + } + else if (higherThanCurve) { + double w_diff = wavelength_ - Wavelengths[curve + 1]; + double new_wavelength = Wavelengths[curve + 1] - w_diff; + double fact1 = (Wavelengths[curve + 1] - new_wavelength) / (Wavelengths[curve + 1] - Wavelengths[curve - 1]); + double fact2 = (new_wavelength - Wavelengths[curve - 1]) / (Wavelengths[curve + 1] - Wavelengths[curve - 1]); + + for (int i = 0; i < ArrayLength2; i++) { + double val = ArrayLcVoltagesRetLoaded[i][curve]; + ArrayLcVoltagesRetCurve[i][0] = val; + double curve1aVal = getValueFromArray(val, curve - 2, curve - 3); + double curve1bVal = getValueFromArray(val, curve - 1, curve - 3); + double curve2aVal = getValueFromArray(val, curve + 1, curve); + double curve2bVal = getValueFromArray(val, curve + 2, curve); + ArrayLcVoltagesRetCurve[i][1] = 2 * curve2aVal - ((curve1aVal * fact1) + (curve2aVal * fact2)); + ArrayLcVoltagesRetCurve[i][2] = 2 * curve2bVal - ((curve1bVal * fact1) + (curve2bVal * fact2)); + } + + } + else if (isCurve) { + for (int i = 0; i < ArrayLength2; i++) { + double val = ArrayLcVoltagesRetLoaded[i][curve]; + ArrayLcVoltagesRetCurve[i][0] = val; + double curveVal1 = getValueFromArray(val, curve + 1, curve); + double curveVal2 = getValueFromArray(val, curve + 2, curve); + ArrayLcVoltagesRetCurve[i][1] = curveVal1; + ArrayLcVoltagesRetCurve[i][2] = curveVal2; + } + } + else { + + double fact1 = (Wavelengths[curve + 1] - wavelength_) / (Wavelengths[curve + 1] - Wavelengths[curve - 1]); + double fact2 = (wavelength_ - Wavelengths[curve - 1]) / (Wavelengths[curve + 1] - Wavelengths[curve - 1]); + + for (int i = 0; i < ArrayLength2; i++) { + double val = ArrayLcVoltagesRetLoaded[i][curve]; + ArrayLcVoltagesRetCurve[i][0] = val; + double curve1aVal = getValueFromArray(val, curve - 2, curve - 3); + double curve1bVal = getValueFromArray(val, curve - 1, curve - 3); + double curve2aVal = getValueFromArray(val, curve + 1, curve); + double curve2bVal = getValueFromArray(val, curve + 2, curve); + if (fact1 == 1 || fact1 == 0) { + ArrayLcVoltagesRetCurve[i][1] = (curve1aVal * fact1) + (curve2aVal * fact2); + ArrayLcVoltagesRetCurve[i][2] = (curve1bVal * fact1) + (curve2bVal * fact2); + } + else if (fact1 > fact2) { + ArrayLcVoltagesRetCurve[i][1] = (curve1aVal * fact1) + (curve2aVal * fact2); + ArrayLcVoltagesRetCurve[i][2] = (curve1bVal * fact1) + (curve2bVal * fact2); + } + else if (fact1 < fact2) { + ArrayLcVoltagesRetCurve[i][1] = (curve1aVal * fact1) + (curve2aVal * fact2); + ArrayLcVoltagesRetCurve[i][2] = (curve1bVal * fact1) + (curve2bVal * fact2); + } + else { + ArrayLcVoltagesRetCurve[i][1] = (curve1aVal * fact1) + (curve2aVal * fact2); + ArrayLcVoltagesRetCurve[i][2] = (curve1bVal * fact1) + (curve2bVal * fact2); + } + } + } + } + /*ArrayLcVoltagesRetCurve[2][0] = curve; + ArrayLcVoltagesRetCurve[2][1] = isCurve; + ArrayLcVoltagesRetCurve[2][2] = wavelength_; + ArrayLcVoltagesRetCurve[3][0] = Wavelengths[2]; + ArrayLcVoltagesRetCurve[3][1] = Wavelengths[4]; + ArrayLcVoltagesRetCurve[3][2] = Wavelengths[7];*/ +} + +double MeadowlarkLC::getValueFromArray(double val, int x, int curve_idx) { + for (int i = 0; i < ArrayLength2; i++) { + if (val == ArrayLcVoltagesRetLoaded[i][curve_idx]) { + return ArrayLcVoltagesRetLoaded[i][x]; + } + else if (val > ArrayLcVoltagesRetLoaded[i][curve_idx] && val < ArrayLcVoltagesRetLoaded[i + 1][curve_idx]) { + double diff = ArrayLcVoltagesRetLoaded[i + 1][curve_idx] - ArrayLcVoltagesRetLoaded[i][curve_idx]; + double retDiff = ArrayLcVoltagesRetLoaded[i][x] - ArrayLcVoltagesRetLoaded[i + 1][x]; + double excess = retDiff * ((val - ArrayLcVoltagesRetLoaded[i][curve_idx]) / diff); + return ArrayLcVoltagesRetLoaded[i][x] - excess; + } + } + return 0.5; +} + +void MeadowlarkLC::loadDefault() { + + for (int i = 0; i < ArrayLengthDefault; i++) { + ArrayLcVoltagesRetLoaded[i][0] = ArrayDefaultLcVoltagesRet[i][0]; + ArrayLcVoltagesRetLoaded[i][1] = ArrayDefaultLcVoltagesRet[i][1]; + ArrayLcVoltagesRetLoaded[i][2] = ArrayDefaultLcVoltagesRet[i][2]; + + ArrayLcVoltagesRetCurve[i][0] = ArrayDefaultLcVoltagesRet[i][0]; + ArrayLcVoltagesRetCurve[i][1] = ArrayDefaultLcVoltagesRet[i][1]; + ArrayLcVoltagesRetCurve[i][2] = ArrayDefaultLcVoltagesRet[i][2]; + } + + ArrayLength2 = ArrayLengthDefault; +} + +void MeadowlarkLC::loadResource(int ID) { + lcCurve_ = ""; + + HMODULE handle = GetCurrentModule(); + HRSRC hRes = FindResource(handle, MAKEINTRESOURCE(ID), MAKEINTRESOURCE(TEXTFILE)); + + if (NULL != hRes) + { + HGLOBAL hData = LoadResource(handle, hRes); + if (NULL != hData) + { + DWORD dataSize = SizeofResource(handle, hRes); + char* data = (char*)LockResource(hData); + lcCurve_.assign(data, dataSize); + + //::OutputDebugString(lcCurve_.c_str()); // Print as ASCII text + + //char* buffer = new char[dataSize+1]; + //::memcpy(buffer, data, dataSize); + //buffer[dataSize] = 0; // NULL terminator + //::OutputDebugString(buffer); // Print as ASCII text + //delete[] buffer; + } + } +} + +void MeadowlarkLC::setSystemSpecificActivationKey(std::string serialNum) { + SystemSpecificActivationKey = "OPS-MeadowlarkLcOpenSource"; +} + + +//////////////// ---- ToDo ---- ////////////////// +// +// 1. Added Exercise routine in a new thread so that it does not stop device interface + + + diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h new file mode 100644 index 000000000..6cf2904c9 --- /dev/null +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h @@ -0,0 +1,209 @@ +/////////////////////////////////////////////////////////////////////////////// +// FILE: MeadowlarkLC.h +// PROJECT: Micro-Manager +// SUBSYSTEM: DeviceAdapters +//----------------------------------------------------------------------------- +// DESCRIPTION: MeadowlarkLC Device Adapter for Four Channel Digital Interface (D3050) and API family +// +// Copyright � 2009 - 2014, Marine Biological Laboratory +// +// LICENSE (Berkeley Software Distribution License): Redistribution and use in source and binary forms, +// with or without modification, are permitted provided that the following conditions are met: +// +// 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. +// 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer +// in the documentation and/or other materials provided with the distribution. +// 3. Neither the name of the Marine Biological Laboratory nor the names of its contributors may be used to endorse or promote products +// derived from this software without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE +// COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +// (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +// HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) +// ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +// +// The views and conclusions contained in the software and documentation are those of the authors and should not be interpreted as +// representing official policies, either expressed or implied, of any organization. +// +// Developed at the Laboratory of Rudolf Oldenbourg at the Marine Biological Laboratory in Woods Hole, MA. +// +// +// AUTHOR: Amitabh Verma +// +// Notes: Refer MeadowlarkLC.cpp for ChangeLog, ToDo and other information + +#ifndef _MEADOWLARKLC_H_ +#define _MEADOWLARKLC_H_ + +#include +#include + +#include "DeviceBase.h" + +////////////////////////////////////////////////////////////////////////////// +#define ERR_PORT_CHANGE_FORBIDDEN 109 +#define ERR_INVALID_DEVICE 102 +#define ERR_INVALID_SERIAL_NUMBER 103 +#define ERR_INVALID_LCSERIAL_NUMBER 104 +#define ERR_INVALID_ACTIVE_LCS 105 +#define ERR_INVALID_ACTIVATION_KEY 106 +#define ERR_INVALID_LC_UNPAIRED 107 +#define ERR_INVALID_LC_SELECTION 108 +#define ERR_INVALID_LC_FILE 109 +#define flagsandattrs 0x40000000 + + +class MeadowlarkLC : public CGenericBase +{ +public: + MeadowlarkLC(); + ~MeadowlarkLC(); + + // Device API + // --------- + int Initialize(); + int Shutdown(); + + void GetName(char* pszName) const; + bool Busy(); + int GetVLCSerialAnswer(const char* portName, const char* term, std::string& ans); + + + // int Initialize(MM::Device& device, MM::Core& core); + int DeInitialize() { initialized_ = false; return DEVICE_OK; }; + bool Initialized() { return initialized_; }; + void loadResource(int ID); + + // device discovery + + // action interface + // --------------- + int OnPort(MM::PropertyBase* pProp, MM::ActionType eAct); + int OnBaud(MM::PropertyBase* pProp, MM::ActionType eAct); + int OnBriefMode(MM::PropertyBase* pProp, MM::ActionType eAct); + + int OnSerialNumber(MM::PropertyBase* pProp, MM::ActionType eAct); + int OnDevAdapterSerialNumber(MM::PropertyBase* pProp, MM::ActionType eAct); + int OnActivationKey(MM::PropertyBase* pProp, MM::ActionType eAct); + int OnControllerType(MM::PropertyBase* pProp, MM::ActionType eAct); + int OnControllerLCType(MM::PropertyBase* pProp, MM::ActionType eAct); + int OnTemperature(MM::PropertyBase* pProp, MM::ActionType eAct); + int OnNumDevices(MM::PropertyBase* pProp, MM::ActionType eAct); + int OnNumTotalLCs(MM::PropertyBase* pProp, MM::ActionType eAct); + int OnNumActiveLCs(MM::PropertyBase* pProp, MM::ActionType eAct); + int GetDesc(MM::PropertyBase* pProp, MM::ActionType eAct); + + int OnDelay(MM::PropertyBase* pProp, MM::ActionType eAct); + + int OnVoltage(MM::PropertyBase* pProp, MM::ActionType eAct, long index); + int OnRetardance(MM::PropertyBase* pProp, MM::ActionType eAct, long index); + int OnAbsRetardance(MM::PropertyBase* pProp, MM::ActionType eAct, long index); + int OnWavelength(MM::PropertyBase* pProp, MM::ActionType eAct); + + int OnTneDuaration(MM::PropertyBase* pProp, MM::ActionType eAct); + int OnTneAmplitude(MM::PropertyBase* pProp, MM::ActionType eAct); + + // int OnEpilogueL (MM::PropertyBase* pProp, MM::ActionType eAct); + int OnNumPalEls(MM::PropertyBase* pProp, MM::ActionType eAct); + int OnPalEl(MM::PropertyBase* pProp, MM::ActionType eAct, long index); + int OnSendToMeadowlarkLC(MM::PropertyBase* pProp, MM::ActionType eAct); + int OnGetFromMeadowlarkLC(MM::PropertyBase* pProp, MM::ActionType eAct); + +private: + HANDLE dev_Handle, pipe0, pipe1; + UINT devcnt, i; + UINT USB_PID; + GUID theGUID; + std::string cur_dev_name; + int cur_dev; + double g_ControllerDeviceTypeVFac; + double VoltageToRetFactor; + double RetToVoltageFactor; + double valTNE; + double wavelength_; // the cached value + int numberofCurves; // default is 1, will change based on import + int ArrayLength2; + + double ArrayLcVoltagesRetLoaded[1000][21]; // allow 7 curves import from csv + double ArrayLcVoltagesRetCurve[1000][3]; + double ConfigData[250][3]; + double Wavelengths[11]; + + std::vector devNameList; + std::string serialnum_; + std::string activationKey_; + std::string SystemSpecificActivationKey; + std::string controllerType_; + std::string controllerLCType_; + std::string controllerLCType_Curve; + std::string descriptionUnparsed_; + std::string totalLCsMsg; + std::string lcCurve_; + + double temperature_; // the cached value + // Command exchange with MMCore + std::string description_; + + bool initialized_; + double answerTimeoutMs_; + bool briefModeQ_; + + long numTotalDevices_; // total number of LCs + long numTotalLCs_; // total number of LCs + long numActiveLCs_; // number of actively controlled LCs (the actively controlled LCs appear first in the list of retardance values in the L-command) + double retardance_[26]; // retardance values of total number of LCs; I made the index 8, a high number unlikely to be exceeded by the variLC hardware + double voltage_[26]; + std::string epilogueL_; // added at the end of every L command to account for uncontrolled LCs + long numPalEls_; // total number of palette elements + std::string palEl_[99]; // array of palette elements, index is total number of elements + double palette_[26][10]; // array of 26 palettes supporting 10 LCs + // std::string currRet_; + + double tneDuration_; + double tneAmplitude_; + bool interruptExercise_; + + std::string sendToMeadowlarkLC_; + std::string getFromMeadowlarkLC_; + MM::MMTime delay; + MM::MMTime changedTime_; // is only required when writing to device and setting voltage not for other operations + + std::vector getNumbersFromMessage(std::string variLCmessage, bool prefixQ); + std::string RemoveChars(const std::string& source, const std::string& chars); + std::string IntToString(int N); + std::string DoubleToString(double N); + int StringToInt(std::string str); + double StringToDouble(std::string str); + + void hexconvert(char* text, unsigned char bytes[]); + + double VoltageToRetardance(double volt, long index); + double RetardanceToVoltage(double retardance, long index); + double RetardanceToVoltage(long wIndex, double AbsRetardance); + + void SendVoltageToDevice(int volt16bit, long index); + void SetTneToDevice(int amplitude, double duration); + + double round(double number); + double roundN(double number, int precision); + double getValueFromArray(double val, int y, int curve_idx); + void doExercise(int n); + void import(std::string calibCurveFilename); + void importConfig(); + void convertStringtoStringArray(std::string str); + void exportCurve(); + void exportConfig(); + void clearConfig(); + void exportloadedCurve(); + void loadDefault(); + void generateCurve(); + void controllerLcTypeChange(); + + void setSystemSpecificActivationKey(std::string SerialN); + bool checkCalibFile(std::string strings); + bool checkConfigFile(std::string strings); +}; + + +#endif //_MEADOWLARKLC_H_ diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj new file mode 100644 index 000000000..318e08892 --- /dev/null +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj @@ -0,0 +1,175 @@ + + + + + Debug + Win32 + + + Release + Win32 + + + Debug + x64 + + + Release + x64 + + + + + + + + + + + {b8c95f39-54bf-40a9-807b-598df2821d55} + + + + 16.0 + Win32Proj + {bd7b178b-b026-48fc-b7bd-c5d5257b3a20} + MeadowlarkLC + 10.0 + + + + DynamicLibrary + true + v142 + Unicode + + + DynamicLibrary + false + v142 + true + Unicode + + + DynamicLibrary + true + v142 + Unicode + + + DynamicLibrary + false + v142 + true + Unicode + + + + + + + + + + + + + + + + + + + + + + + + + + + + + true + "$(MM_3RDPARTYPRIVATE)\Meadowlark_V104\lib";$(LibraryPath) + $(MM_3RDPARTYPRIVATE)\Meadowlark_V104\include;$(IncludePath) + + + false + "$(MM_3RDPARTYPRIVATE)\Meadowlark_V104\lib";$(LibraryPath) + $(MM_3RDPARTYPRIVATE)\Meadowlark_V104\include;$(IncludePath) + + + true + "$(MM_3RDPARTYPRIVATE)\Meadowlark_V104\lib64";$(LibraryPath) + $(MM_3RDPARTYPRIVATE)\Meadowlark_V104\include;$(IncludePath) + + + false + "$(MM_3RDPARTYPRIVATE)\Meadowlark_V104\lib64";$(LibraryPath) + $(MM_3RDPARTYPRIVATE)\Meadowlark_V104\include;$(IncludePath) + + + + true + WIN32;_DEBUG;MEADOWLARKLC_EXPORTS;_WINDOWS;_USRDLL;%(PreprocessorDefinitions) + true + + + Windows + true + usbdrvd32.lib;%(AdditionalDependencies) + false + + + + + true + true + true + WIN32;NDEBUG;MEADOWLARKLC_EXPORTS;_WINDOWS;_USRDLL;%(PreprocessorDefinitions) + true + + + Windows + true + true + true + usbdrvd32.lib;%(AdditionalDependencies) + false + + + + + true + _DEBUG;MEADOWLARKLC_EXPORTS;_WINDOWS;_USRDLL;%(PreprocessorDefinitions) + true + + + Windows + true + usbdrvd64.lib;%(AdditionalDependencies) + false + + + + + true + true + true + NDEBUG;MEADOWLARKLC_EXPORTS;_WINDOWS;_USRDLL;%(PreprocessorDefinitions) + true + + + Windows + true + true + true + usbdrvd64.lib;%(AdditionalDependencies) + false + + + + + + \ No newline at end of file diff --git a/micromanager.sln b/micromanager.sln index c166c9cbf..d60cceb9c 100644 --- a/micromanager.sln +++ b/micromanager.sln @@ -435,10 +435,13 @@ EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "NIDAQ", "DeviceAdapters\NIDAQ\NIDAQ.vcxproj", "{51AC9E8C-8BD5-4EFE-8571-6EE74D0BC22B}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "ThorlabsPM100x", "DeviceAdapters\ThorlabsPM100x\ThorlabsPM100x.vcxproj", "{5583AC3C-328B-4969-978A-63AED0DD2258}" +EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "UniversalMMHubSerial", "DeviceAdapters\UniversalMMHubSerial\UniversalMMHubSerial.vcxproj", "{870B45D3-5EA6-47C3-9A86-3372CE0A0436}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "UniversalMMHubUsb", "DeviceAdapters\UniversalMMHubUsb\UniversalMMHubUsb.vcxproj", "{9A33047E-4E1F-4C96-8BBA-FB9610D75373}" EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "MeadowlarkLC", "DeviceAdapters\MeadowlarkLC\MeadowlarkLC.vcxproj", "{BD7B178B-B026-48FC-B7BD-C5D5257B3A20}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|x64 = Debug|x64 @@ -1321,6 +1324,10 @@ Global {9A33047E-4E1F-4C96-8BBA-FB9610D75373}.Debug|x64.Build.0 = Debug|x64 {9A33047E-4E1F-4C96-8BBA-FB9610D75373}.Release|x64.ActiveCfg = Release|x64 {9A33047E-4E1F-4C96-8BBA-FB9610D75373}.Release|x64.Build.0 = Release|x64 + {BD7B178B-B026-48FC-B7BD-C5D5257B3A20}.Debug|x64.ActiveCfg = Debug|x64 + {BD7B178B-B026-48FC-B7BD-C5D5257B3A20}.Debug|x64.Build.0 = Debug|x64 + {BD7B178B-B026-48FC-B7BD-C5D5257B3A20}.Release|x64.ActiveCfg = Release|x64 + {BD7B178B-B026-48FC-B7BD-C5D5257B3A20}.Release|x64.Build.0 = Release|x64 EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE From 6381567e6f1bd1ad609c9828fdfb79bb9375718a Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Mon, 27 Jun 2022 19:37:42 -0700 Subject: [PATCH 02/29] Update 3rdparty files location --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj index 318e08892..1cc05c4df 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj @@ -91,23 +91,23 @@ true - "$(MM_3RDPARTYPRIVATE)\Meadowlark_V104\lib";$(LibraryPath) - $(MM_3RDPARTYPRIVATE)\Meadowlark_V104\include;$(IncludePath) + "$(MM_3RDPARTYPRIVATE)\Meadowlark\V104\lib";$(LibraryPath) + $(MM_3RDPARTYPRIVATE)\Meadowlark\V104\include;$(IncludePath) false - "$(MM_3RDPARTYPRIVATE)\Meadowlark_V104\lib";$(LibraryPath) - $(MM_3RDPARTYPRIVATE)\Meadowlark_V104\include;$(IncludePath) + "$(MM_3RDPARTYPRIVATE)\Meadowlark\V104\lib";$(LibraryPath) + $(MM_3RDPARTYPRIVATE)\Meadowlark\V104\include;$(IncludePath) true - "$(MM_3RDPARTYPRIVATE)\Meadowlark_V104\lib64";$(LibraryPath) - $(MM_3RDPARTYPRIVATE)\Meadowlark_V104\include;$(IncludePath) + "$(MM_3RDPARTYPRIVATE)\Meadowlark\V104\lib64";$(LibraryPath) + $(MM_3RDPARTYPRIVATE)\Meadowlark\V104\include;$(IncludePath) false - "$(MM_3RDPARTYPRIVATE)\Meadowlark_V104\lib64";$(LibraryPath) - $(MM_3RDPARTYPRIVATE)\Meadowlark_V104\include;$(IncludePath) + "$(MM_3RDPARTYPRIVATE)\Meadowlark\V104\lib64";$(LibraryPath) + $(MM_3RDPARTYPRIVATE)\Meadowlark\V104\include;$(IncludePath) From 585a07fed7d7ce80cd5e4f213ca020919b3bdcb6 Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Tue, 28 Jun 2022 17:31:24 -0700 Subject: [PATCH 03/29] remove Win32 support --- .../MeadowlarkLC/MeadowlarkLC.vcxproj | 71 ------------------- 1 file changed, 71 deletions(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj index 1cc05c4df..ffc8baf63 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj @@ -1,14 +1,6 @@ - - Debug - Win32 - - - Release - Win32 - Debug x64 @@ -37,19 +29,6 @@ 10.0 - - DynamicLibrary - true - v142 - Unicode - - - DynamicLibrary - false - v142 - true - Unicode - DynamicLibrary true @@ -68,16 +47,6 @@ - - - - - - - - - - @@ -89,16 +58,6 @@ - - true - "$(MM_3RDPARTYPRIVATE)\Meadowlark\V104\lib";$(LibraryPath) - $(MM_3RDPARTYPRIVATE)\Meadowlark\V104\include;$(IncludePath) - - - false - "$(MM_3RDPARTYPRIVATE)\Meadowlark\V104\lib";$(LibraryPath) - $(MM_3RDPARTYPRIVATE)\Meadowlark\V104\include;$(IncludePath) - true "$(MM_3RDPARTYPRIVATE)\Meadowlark\V104\lib64";$(LibraryPath) @@ -109,36 +68,6 @@ "$(MM_3RDPARTYPRIVATE)\Meadowlark\V104\lib64";$(LibraryPath) $(MM_3RDPARTYPRIVATE)\Meadowlark\V104\include;$(IncludePath) - - - true - WIN32;_DEBUG;MEADOWLARKLC_EXPORTS;_WINDOWS;_USRDLL;%(PreprocessorDefinitions) - true - - - Windows - true - usbdrvd32.lib;%(AdditionalDependencies) - false - - - - - true - true - true - WIN32;NDEBUG;MEADOWLARKLC_EXPORTS;_WINDOWS;_USRDLL;%(PreprocessorDefinitions) - true - - - Windows - true - true - true - usbdrvd32.lib;%(AdditionalDependencies) - false - - true From 6c20ca9b332db110804af90be478bf3760727c9d Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Wed, 29 Jun 2022 16:19:47 -0700 Subject: [PATCH 04/29] fix bug in OnVoltage Updated device adapter for consistent units (Volts) of Voltage input and output. Retardance is updated when voltage is changed, and vice versa --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp | 137 +++++++++++-------- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h | 1 + 2 files changed, 84 insertions(+), 54 deletions(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp index 6923450e3..225a205f8 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp @@ -805,15 +805,15 @@ int MeadowlarkLC::Initialize() // Voltage controls for (long i = 0; i < numActiveLCs_; ++i) { ostringstream s; - s << "Voltage (mV) LC-" << char(65 + i); + s << "Voltage (V) LC-" << char(65 + i); pActX = new CPropertyActionEx(this, &MeadowlarkLC::OnVoltage, i); - CreateProperty(s.str().c_str(), "7500", MM::Integer, true, pActX); + CreateProperty(s.str().c_str(), "7.500", MM::Float, false, pActX); if (controllerType_ == g_ControllerDeviceType10V) { - SetPropertyLimits(s.str().c_str(), 0, 10000); + SetPropertyLimits(s.str().c_str(), 0, 10.0); } else { - SetPropertyLimits(s.str().c_str(), 0, 20000); + SetPropertyLimits(s.str().c_str(), 0, 20.0); } } @@ -829,7 +829,7 @@ int MeadowlarkLC::Initialize() // Absolute Retardance controls -- after Voltage controls for (long i = 0; i < numActiveLCs_; ++i) { ostringstream s; - s << "Retardance LC-" << char(65 + i) << " [in nm.]"; + s << "Retardance LC-" << char(65 + i) << " [in nm]"; pActX = new CPropertyActionEx(this, &MeadowlarkLC::OnAbsRetardance, i); CreateProperty(s.str().c_str(), "100", MM::Float, true, pActX); } @@ -1100,8 +1100,31 @@ int MeadowlarkLC::OnRetardance(MM::PropertyBase* pProp, MM::ActionType eAct, lon if (eAct == MM::BeforeGet) { - if (index + 1 > 0) { - pProp->Set(retardance_[index]); + if (index + 1 > 0) + { + double voltage = GetVoltage(index); // in mV + //double voltage = voltage_[index]; + double maxV = 10000; + if (controllerType_ == g_ControllerDeviceType20V_D3060HV || controllerType_ == g_ControllerDeviceType20V_D5020) { + maxV = 20000; + } + + if (voltage >= 0 && voltage <= maxV) { + double retardance = VoltageToRetardance(voltage, index); + + //if the new retardance is the same as the old retardance, then do nothing + if (retardance_[index] == retardance) { + return DEVICE_OK; + } + retardance_[index] = retardance; + pProp->Set(retardance); + + //update abs retardance property + ostringstream s; + s << "Retardance LC-" << char(65 + index) << " [in nm]"; + std::string s2 = DoubleToString(retardance * wavelength_); + SetProperty(s.str().c_str(), s2.c_str()); + } } else { return DEVICE_INVALID_PROPERTY_VALUE; @@ -1111,6 +1134,7 @@ int MeadowlarkLC::OnRetardance(MM::PropertyBase* pProp, MM::ActionType eAct, lon { double retardance = retardance_[index]; double retardanceT; + // read value from property pProp->Get(retardanceT); @@ -1122,7 +1146,6 @@ int MeadowlarkLC::OnRetardance(MM::PropertyBase* pProp, MM::ActionType eAct, lon } // write retardance out to device.... - retardanceT = ceilf(retardanceT * 10000) / 10000; double voltage = round(RetardanceToVoltage(retardanceT, index)); @@ -1163,15 +1186,17 @@ int MeadowlarkLC::OnRetardance(MM::PropertyBase* pProp, MM::ActionType eAct, lon if (voltage_[index] == voltage) { return DEVICE_OK; } + voltage_[index] = voltage; + + //update Voltage property + ostringstream s; + s << "Voltage (V) LC-" << char(65+index); + std::string s2 = DoubleToString(voltage/1000); // in V + SetProperty(s.str().c_str(), s2.c_str()); // write voltage out to device.... - //ostringstream s; - //s << "Voltage (mV) LC-" << char(65+index); - //std::string s2 = DoubleToString(voltage); - //SetProperty(s.str().c_str(), s2.c_str()); int volt16bit = static_cast(voltage); SendVoltageToDevice(volt16bit, index); - voltage_[index] = voltage; // changedTime_ = GetCurrentMMTime(); } @@ -1201,70 +1226,49 @@ int MeadowlarkLC::OnVoltage(MM::PropertyBase* pProp, MM::ActionType eAct, long i if (initialized_) { if (eAct == MM::BeforeGet) { - - BYTE query_volt[] = { 'l', 'd', ':', char(index + 49), ',', '?', '\r' }; - BYTE statusRead[64]; - - USBDRVD_BulkWrite(dev_Handle, 1, query_volt, sizeof(query_volt)); /* send ld:n,? command */ - - USBDRVD_BulkRead(dev_Handle, 0, statusRead, sizeof(statusRead)); /* read status response */ - - std::string ans = ((char*)statusRead); - - size_t length; - char buffer[64]; - length = ans.copy(buffer, 5, 5); - buffer[length] = '\n'; - - //int voltInt = StringToInt(buffer) * 1000/g_ControllerDeviceTypeVFac; - - double voltage = round(StringToInt(buffer) * 1000 / g_ControllerDeviceTypeVFac); + double voltage = GetVoltage(index); // in mV double maxV = 10000; if (controllerType_ == g_ControllerDeviceType20V_D3060HV || controllerType_ == g_ControllerDeviceType20V_D5020) { maxV = 20000; } - if (index + 1 >= 0 && voltage > 0 && voltage <= maxV) { - - pProp->Set(voltage); + if (index + 1 >= 0 && voltage >= 0 && voltage <= maxV) { + //if the new voltage is the same as the old voltage, then do nothing if (voltage_[index] == voltage) { return DEVICE_OK; } voltage_[index] = voltage; - - double Retardance = VoltageToRetardance(voltage, index); - retardance_[index] = Retardance; - ostringstream s; - s << "Retardance LC-" << char(65 + index) << " [in waves]"; - std::string s2 = DoubleToString(Retardance); - SetProperty(s.str().c_str(), s2.c_str()); - - } - else { - // return DEVICE_INVALID_PROPERTY_VALUE; + pProp->Set(voltage / 1000); // pProp is in V } } else if (eAct == MM::AfterSet) { double voltage; - // read value from property + // read value from property, in Volts pProp->Get(voltage); + voltage *= 1000; // now in mV - if (voltage_[index] == voltage) { - return DEVICE_OK; + double maxV = 10000; + if (controllerType_ == g_ControllerDeviceType20V_D3060HV || controllerType_ == g_ControllerDeviceType20V_D5020) { + maxV = 20000; } - // double Retardance = VoltageToRetardance(voltage); - // retardance_[index] = Retardance; - // write voltage out to device.... + if (index+1 >= 0 && voltage >= 0 && voltage <= maxV) { - double v = ((voltage / 1000) * g_ControllerDeviceTypeVFac); - int volt16bit = static_cast(v); + //if the new voltage is the same as the old voltage, then do nothing + if (voltage_[index] == voltage) { + return DEVICE_OK; + } + voltage_[index] = voltage; - SendVoltageToDevice(volt16bit, index); + //send voltage to device + double v = voltage / 1000 * g_ControllerDeviceTypeVFac; + int volt16bit = static_cast(v); + SendVoltageToDevice(volt16bit, index); + } } } return DEVICE_OK; @@ -1927,6 +1931,31 @@ double MeadowlarkLC::roundN(double val, int precision) return val; } +double MeadowlarkLC::GetVoltage(long index) { + // returns voltage in mV + + double voltage = -1; + + if (index + 1 > 0) { + BYTE query_volt[] = { 'l', 'd', ':', char(index + 49), ',', '?', '\r' }; + BYTE statusRead[64]; + + USBDRVD_BulkWrite(dev_Handle, 1, query_volt, sizeof(query_volt)); /* send ld:n,? command */ + USBDRVD_BulkRead(dev_Handle, 0, statusRead, sizeof(statusRead)); /* read status response */ + + std::string ans = ((char*)statusRead); + + size_t length; + char buffer[64]; + length = ans.copy(buffer, 5, 5); + buffer[length] = '\n'; + + voltage = round(StringToInt(buffer) * 1000 / g_ControllerDeviceTypeVFac); // in mV + } + + return voltage; +} + double MeadowlarkLC::VoltageToRetardance(double volt, long index) { double retardance = 0; diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h index 6cf2904c9..752990461 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h @@ -181,6 +181,7 @@ class MeadowlarkLC : public CGenericBase double VoltageToRetardance(double volt, long index); double RetardanceToVoltage(double retardance, long index); double RetardanceToVoltage(long wIndex, double AbsRetardance); + double GetVoltage(long index); void SendVoltageToDevice(int volt16bit, long index); void SetTneToDevice(int amplitude, double duration); From 51dbb6c1f4fbf355170d5f5297781bf80e6bcfdc Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Wed, 29 Jun 2022 16:50:53 -0700 Subject: [PATCH 05/29] Update device adapter version number and leave TODO comments Left TODO comments and updated Serial Number and Device Adapter Version Number fields --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp | 13 ++++++++----- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h | 2 +- 2 files changed, 9 insertions(+), 6 deletions(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp index 225a205f8..937ecd663 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp @@ -175,7 +175,7 @@ const char* g_ControllerDescriptionInfo = "Description Info"; const std::string g_Nonedetected = "None detected"; const LPCSTR g_About = "MeadowlarkLC Device Adapter for Micro-Manager and use with OpenPolScope Micro-Manager plugin. \n Please refer to http://www.openpolscope.org for more information."; -const char* g_Dev_Adapter_Ver = "1.00.03"; +const char* g_Dev_Adapter_Ver = "1.1.0"; using namespace std; const HMODULE GetCurrentModule() @@ -713,14 +713,14 @@ int MeadowlarkLC::Initialize() if (DEVICE_OK != ret) return ret; - // Version number + // Controller Serial number CPropertyAction* pAct = new CPropertyAction(this, &MeadowlarkLC::OnSerialNumber); - ret = CreateProperty("Version Number", "Version Number Not Found", MM::String, true, pAct); + ret = CreateProperty("Controller Serial Number", "Serial Number Not Found", MM::String, true, pAct); if (ret != DEVICE_OK) return ret; // Device Adapter Version number - pAct = new CPropertyAction(this, &MeadowlarkLC::OnDevAdapterSerialNumber); + pAct = new CPropertyAction(this, &MeadowlarkLC::OnDevAdapterVersionNumber); ret = CreateProperty("Device Adapter Version Number", "Device Adapter Version Number Not Found", MM::String, true, pAct); if (ret != DEVICE_OK) return ret; @@ -1328,7 +1328,7 @@ int MeadowlarkLC::OnSerialNumber(MM::PropertyBase* pProp, MM::ActionType eAct) return DEVICE_OK; } -int MeadowlarkLC::OnDevAdapterSerialNumber(MM::PropertyBase* pProp, MM::ActionType eAct) +int MeadowlarkLC::OnDevAdapterVersionNumber(MM::PropertyBase* pProp, MM::ActionType eAct) { if (eAct == MM::BeforeGet) { @@ -1957,6 +1957,7 @@ double MeadowlarkLC::GetVoltage(long index) { } double MeadowlarkLC::VoltageToRetardance(double volt, long index) { + //TODO: voltage to retardance conversion does not work for low voltages (<2 V) double retardance = 0; double FacRetardance = 0; @@ -2017,6 +2018,8 @@ double MeadowlarkLC::VoltageToRetardance(double volt, long index) { } double MeadowlarkLC::RetardanceToVoltage(double retard, long index) { + // retardance to voltage conversion does not work for high retardances (>= 1.6). + // voltage cannot be set to Vmax double voltage = 0; double FacRetardance = 0; diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h index 752990461..d71e9e980 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h @@ -84,7 +84,7 @@ class MeadowlarkLC : public CGenericBase int OnBriefMode(MM::PropertyBase* pProp, MM::ActionType eAct); int OnSerialNumber(MM::PropertyBase* pProp, MM::ActionType eAct); - int OnDevAdapterSerialNumber(MM::PropertyBase* pProp, MM::ActionType eAct); + int OnDevAdapterVersionNumber(MM::PropertyBase* pProp, MM::ActionType eAct); int OnActivationKey(MM::PropertyBase* pProp, MM::ActionType eAct); int OnControllerType(MM::PropertyBase* pProp, MM::ActionType eAct); int OnControllerLCType(MM::PropertyBase* pProp, MM::ActionType eAct); From 3773ba98570997fea1e922b9ad284dc75b53d49b Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Tue, 26 Jul 2022 18:51:37 -0700 Subject: [PATCH 06/29] update change log --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp index 937ecd663..188772180 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp @@ -3,7 +3,7 @@ // PROJECT: Micro-Manager // SUBSYSTEM: DeviceAdapters //----------------------------------------------------------------------------- -// DESCRIPTION: MeadowlarkLC Device Adapter for Four Channel Digital Interface (D3050) and API family +// DESCRIPTION: MeadowlarkLC Device Adapter for Meadowlark Optics liquid crystal controllers // // Copyright � 2009 - 2018, Marine Biological Laboratory // @@ -27,14 +27,19 @@ // representing official policies, either expressed or implied, of any organization. // // Developed at the Laboratory of Rudolf Oldenbourg at the Marine Biological Laboratory in Woods Hole, MA. -// LAST UPDATE: Amitabh Verma, MBL - Aug. 21, 2018 +// LAST UPDATE: Ivan Ivanov, Chan Zuckerberg Biohub - June, 2022 // // // AUTHOR: Amitabh Verma, MBL - Dec. 05, 2012 // -// Issue tracker :---> http://www.openpolscope.org/mantis/ // ToDo List at EOF // +// Change Log - Ivan Ivanov - June 29, 2022 - 1.1.0 +// 1. Updated VS project files to allow compiling the device adapter along with MicroManager nightly builds. +// 2. Fixed bug in OnVoltage function. Function input and output are now both in units of volts. +// 3. Updated OnRetardance function to refresh the LC retardance once LC voltage is set. Similarly for OnVoltage. +// 4. Renamed "Version Number" property to "Controller Serial Number", which is more accurate. +// // Change Log - Amitabh Verma - Aug. 21, 2018 - 1.00.03 // 1. Implemented config file for device adapter that gets written out when not found based on serial number of device. // This config file can be updated with palette element values for different wavelengths and can be set using command eg. "sp 546" From b4bc4c16c1317552de7cfeb1da6554d4dfb20f2b Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Tue, 26 Jul 2022 19:02:55 -0700 Subject: [PATCH 07/29] move ArrayDefaultLcVoltagesRet to header --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp | 203 ------------------ DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h | 206 ++++++++++++++++++- 2 files changed, 205 insertions(+), 204 deletions(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp index 188772180..5c0f7e4d1 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp @@ -201,209 +201,6 @@ const double ConfigDataDefaults[5][3] = { {546,0.28,0.5} }; -const int ArrayLengthDefault = 198; -// LC Calibration curve Voltage(mV) vs Absolute Retardance(nm) -const double ArrayDefaultLcVoltagesRet[ArrayLengthDefault][3] = { - {0,1284.343,1284.343}, - {200,1284.411,1284.411}, - {400,1284.0869,1284.0869}, - {600,1283.8796,1283.8796}, - {800,1283.3625,1283.3625}, - {800.0002,1283.2228,1283.2228}, - {800.0005,1283.3013,1283.3013}, - {800.0013,1283.415,1283.415}, - {800.0025,1283.3468,1283.3468}, - {800.0045,1283.4783,1283.4783}, - {800.0074,1283.3376,1283.3376}, - {800.0117,1283.3345,1283.3345}, - {800.0179,1283.4308,1283.4308}, - {800.0264,1283.496,1283.496}, - {800.0377,1283.4891,1283.4891}, - {800.0527,1283.4348,1283.4348}, - {800.0721,1283.7001,1283.7001}, - {800.0969,1283.6556,1283.6556}, - {800.128,1283.7085,1283.7085}, - {800.1666,1283.7365,1283.7365}, - {800.214,1283.7697,1283.7697}, - {800.2716,1283.6506,1283.6506}, - {800.3411,1283.7167,1283.7167}, - {800.424,1283.6982,1283.6982}, - {800.5223,1283.7743,1283.7743}, - {800.638,1283.8627,1283.8627}, - {800.7734,1283.7518,1283.7518}, - {800.9308,1283.8488,1283.8488}, - {801.113,1283.8833,1283.8833}, - {801.3225,1283.8304,1283.8304}, - {801.5625,1283.8893,1283.8893}, - {801.8361,1283.8992,1283.8992}, - {802.1468,1283.9257,1283.9257}, - {802.4982,1283.9562,1283.9562}, - {802.8941,1284.0687,1284.0687}, - {803.3387,1284.1172,1284.1172}, - {803.8364,1284.0798,1284.0798}, - {804.3917,1284.0042,1284.0042}, - {805.0095,1284.047,1284.047}, - {805.6949,1284.0695,1284.0695}, - {806.4534,1284.1594,1284.1594}, - {807.2906,1284.1851,1284.1851}, - {808.2125,1284.1339,1284.1339}, - {809.2255,1284.2399,1284.2399}, - {810.336,1284.2579,1284.2579}, - {811.5509,1284.3578,1284.3578}, - {812.8775,1284.1702,1284.1702}, - {814.3233,1284.2469,1284.2469}, - {815.8961,1284.1438,1284.1438}, - {817.6041,1284.283,1284.283}, - {819.4559,1284.301,1284.301}, - {821.4603,1284.2782,1284.2782}, - {823.6266,1284.1348,1284.1348}, - {825.9644,1284.2441,1284.2441}, - {828.4838,1284.1818,1284.1818}, - {831.1949,1284.3066,1284.3066}, - {834.1088,1284.2123,1284.2123}, - {837.2363,1284.1847,1284.1847}, - {840.5892,1284.2885,1284.2885}, - {844.1794,1284.2258,1284.2258}, - {848.0192,1284.1924,1284.1924}, - {852.1216,1284.3458,1284.3458}, - {856.4996,1284.1655,1284.1655}, - {861.1669,1284.0703,1284.0703}, - {866.1377,1284.145,1284.145}, - {871.4266,1284.1002,1284.1002}, - {877.0485,1284.0598,1284.0598}, - {883.0189,1284.0197,1284.0197}, - {889.3539,1283.9844,1283.9844}, - {896.0698,1283.9204,1283.9204}, - {903.1836,1283.9547,1283.9547}, - {910.7126,1283.9744,1283.9744}, - {918.675,1283.9253,1283.9253}, - {927.0889,1283.9131,1283.9131}, - {935.9734,1283.7408,1283.7408}, - {945.3481,1283.6477,1283.6477}, - {955.2328,1283.6884,1283.6884}, - {965.6481,1283.6045,1283.6045}, - {976.6151,1283.4708,1283.4708}, - {988.1553,1283.4731,1283.4731}, - {1000.2911,1283.4991,1283.4991}, - {1013.0452,1283.2888,1283.2888}, - {1026.4408,1283.2068,1283.2068}, - {1040.502,1282.854,1282.854}, - {1055.2531,1282.8246,1282.8246}, - {1070.7194,1282.4509,1282.4509}, - {1086.9263,1282.1366,1282.1366}, - {1103.9004,1281.6805,1281.6805}, - {1121.6683,1281.3497,1281.3497}, - {1140.2579,1280.9851,1280.9851}, - {1159.6971,1280.6768,1280.6768}, - {1180.0148,1280.2689,1280.2689}, - {1201.2404,1279.3618,1279.3618}, - {1223.4039,1278.7089,1278.7089}, - {1246.5363,1277.9419,1277.9419}, - {1270.6688,1276.0315,1276.0315}, - {1295.8336,1274.8234,1274.8234}, - {1322.0635,1272.7963,1272.7963}, - {1349.3917,1270.1302,1270.1302}, - {1377.8527,1266.1652,1266.1652}, - {1407.4811,1260.8419,1260.8419}, - {1438.3125,1253.3003,1253.3003}, - {1470.3833,1244.5061,1244.5061}, - {1503.7303,1232.5726,1232.5726}, - {1538.3914,1217.3304,1217.3304}, - {1574.4049,1198.2084,1198.2084}, - {1611.8101,1176.7759,1176.7759}, - {1650.6469,1154.4043,1154.4043}, - {1690.9559,1128.3533,1128.3533}, - {1732.7789,1089,1089}, - {1821.1359,1047.5177,1047.5177}, - {1867.7567,1016.2104,1016.2104}, - {1916.0651,984.7769,984.7769}, - {1966.1063,953.2874,953.2874}, - {2017.9265,920.6101,920.6101}, - {2071.573,887.09,887.09}, - {2127.0933,851.7007,851.7007}, - {2184.5361,816.75,816.75}, - {2305.3887,754.0078,754.0078}, - {2368.8997,721.3992,721.3992}, - {2434.5366,689.3527,689.3527}, - {2502.3521,658.8939,658.8939}, - {2572.3999,628.5602,628.5602}, - {2644.7349,599.2983,599.2983}, - {2719.4126,569.1844,569.1844}, - {2796.4893,544.5,544.5}, - {2958.0703,491.2751,491.2751}, - {3042.6919,468.1365,468.1365}, - {3129.9478,446.146,446.146}, - {3219.8982,425.1326,425.1326}, - {3312.6057,405.4332,405.4332}, - {3408.1331,387.0562,387.0562}, - {3506.5439,369.5298,369.5298}, - {3607.9033,353.7877,353.7877}, - {3712.2771,338.264,338.264}, - {3819.7314,324.5506,324.5506}, - {3930.3347,308.7356,308.7356}, - {4044.1553,296.194,296.194}, - {4161.2627,284.466,284.466}, - {4281.728,272.25,272.25}, - {4533.0195,249.2416,249.2416}, - {4663.9917,240.8623,240.8623}, - {4798.6152,231.4884,231.4884}, - {4936.9644,221.9211,221.9211}, - {5079.1172,214.1089,214.1089}, - {5225.1514,206.1059,206.1059}, - {5375.145,199.4312,199.4312}, - {5529.1787,192.4627,192.4627}, - {5687.3335,186.2214,186.2214}, - {5849.6919,179.7628,179.7628}, - {6016.3364,173.8859,173.8859}, - {6187.3521,168.3429,168.3429}, - {6362.8232,162.9014,162.9014}, - {6542.8379,157.5549,157.5549}, - {6727.4824,152.6496,152.6496}, - {6916.8462,147.6369,147.6369}, - {7111.019,143.0052,143.0052}, - {7310.0918,138.6415,138.6415}, - {7514.1567,134.3855,134.3855}, - {7723.3071,130.3516,130.3516}, - {7937.6372,126.2824,126.2824}, - {8157.2432,122.406,122.406}, - {8382.2217,118.8456,118.8456}, - {8612.6699,115.4299,115.4299}, - {8848.6885,111.6104,111.6104}, - {9090.377,108.5394,108.5394}, - {9337.8359,105.2933,105.2933}, - {9591.1699,102.3992,102.3992}, - {9850.4814,99.3358,99.3358}, - {10115.876,96.4839,96.4839}, - {10387.4609,93.7825,93.7825}, - {10665.3428,91.202,91.202}, - {10949.6318,88.5837,88.5837}, - {11240.4365,86.0813,86.0813}, - {11537.8691,83.6826,83.6826}, - {11842.042,81.2935,81.2935}, - {12153.0684,79.0205,79.0205}, - {12471.0654,76.9506,76.9506}, - {12796.1484,75.0336,75.0336}, - {13128.4346,72.9454,72.9454}, - {13468.0439,70.8509,70.8509}, - {13815.0967,69.1639,69.1639}, - {14169.7139,67.2585,67.2585}, - {14532.0195,65.5513,65.5513}, - {14902.1367,63.9257,63.9257}, - {15280.1924,61.706,61.706}, - {15666.3135,60.4764,60.4764}, - {16060.627,58.9538,58.9538}, - {16463.2637,57.8524,57.8524}, - {16874.3535,55.6492,55.6492}, - {17294.0312,54.4416,54.4416}, - {17722.4277,53.0858,53.0858}, - {18159.6816,51.6723,51.6723}, - {18605.9258,50.635,50.635}, - {19061.3008,49.3032,49.3032}, - {19525.9453,47.6384,47.6384}, - {20000,46.83,46.83} - -}; - /////////////////////////////////////////////////////////////////////////////// // Exported MMDevice API /////////////////////////////////////////////////////////////////////////////// diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h index d71e9e980..032f13aa7 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h @@ -3,7 +3,7 @@ // PROJECT: Micro-Manager // SUBSYSTEM: DeviceAdapters //----------------------------------------------------------------------------- -// DESCRIPTION: MeadowlarkLC Device Adapter for Four Channel Digital Interface (D3050) and API family +// DESCRIPTION: MeadowlarkLC Device Adapter for Meadowlark Optics liquid crystal controllers // // Copyright � 2009 - 2014, Marine Biological Laboratory // @@ -207,4 +207,208 @@ class MeadowlarkLC : public CGenericBase }; +const int ArrayLengthDefault = 198; +// LC Calibration curve Voltage(mV) vs Absolute Retardance(nm) +const double ArrayDefaultLcVoltagesRet[ArrayLengthDefault][3] = { + {0,1284.343,1284.343}, + {200,1284.411,1284.411}, + {400,1284.0869,1284.0869}, + {600,1283.8796,1283.8796}, + {800,1283.3625,1283.3625}, + {800.0002,1283.2228,1283.2228}, + {800.0005,1283.3013,1283.3013}, + {800.0013,1283.415,1283.415}, + {800.0025,1283.3468,1283.3468}, + {800.0045,1283.4783,1283.4783}, + {800.0074,1283.3376,1283.3376}, + {800.0117,1283.3345,1283.3345}, + {800.0179,1283.4308,1283.4308}, + {800.0264,1283.496,1283.496}, + {800.0377,1283.4891,1283.4891}, + {800.0527,1283.4348,1283.4348}, + {800.0721,1283.7001,1283.7001}, + {800.0969,1283.6556,1283.6556}, + {800.128,1283.7085,1283.7085}, + {800.1666,1283.7365,1283.7365}, + {800.214,1283.7697,1283.7697}, + {800.2716,1283.6506,1283.6506}, + {800.3411,1283.7167,1283.7167}, + {800.424,1283.6982,1283.6982}, + {800.5223,1283.7743,1283.7743}, + {800.638,1283.8627,1283.8627}, + {800.7734,1283.7518,1283.7518}, + {800.9308,1283.8488,1283.8488}, + {801.113,1283.8833,1283.8833}, + {801.3225,1283.8304,1283.8304}, + {801.5625,1283.8893,1283.8893}, + {801.8361,1283.8992,1283.8992}, + {802.1468,1283.9257,1283.9257}, + {802.4982,1283.9562,1283.9562}, + {802.8941,1284.0687,1284.0687}, + {803.3387,1284.1172,1284.1172}, + {803.8364,1284.0798,1284.0798}, + {804.3917,1284.0042,1284.0042}, + {805.0095,1284.047,1284.047}, + {805.6949,1284.0695,1284.0695}, + {806.4534,1284.1594,1284.1594}, + {807.2906,1284.1851,1284.1851}, + {808.2125,1284.1339,1284.1339}, + {809.2255,1284.2399,1284.2399}, + {810.336,1284.2579,1284.2579}, + {811.5509,1284.3578,1284.3578}, + {812.8775,1284.1702,1284.1702}, + {814.3233,1284.2469,1284.2469}, + {815.8961,1284.1438,1284.1438}, + {817.6041,1284.283,1284.283}, + {819.4559,1284.301,1284.301}, + {821.4603,1284.2782,1284.2782}, + {823.6266,1284.1348,1284.1348}, + {825.9644,1284.2441,1284.2441}, + {828.4838,1284.1818,1284.1818}, + {831.1949,1284.3066,1284.3066}, + {834.1088,1284.2123,1284.2123}, + {837.2363,1284.1847,1284.1847}, + {840.5892,1284.2885,1284.2885}, + {844.1794,1284.2258,1284.2258}, + {848.0192,1284.1924,1284.1924}, + {852.1216,1284.3458,1284.3458}, + {856.4996,1284.1655,1284.1655}, + {861.1669,1284.0703,1284.0703}, + {866.1377,1284.145,1284.145}, + {871.4266,1284.1002,1284.1002}, + {877.0485,1284.0598,1284.0598}, + {883.0189,1284.0197,1284.0197}, + {889.3539,1283.9844,1283.9844}, + {896.0698,1283.9204,1283.9204}, + {903.1836,1283.9547,1283.9547}, + {910.7126,1283.9744,1283.9744}, + {918.675,1283.9253,1283.9253}, + {927.0889,1283.9131,1283.9131}, + {935.9734,1283.7408,1283.7408}, + {945.3481,1283.6477,1283.6477}, + {955.2328,1283.6884,1283.6884}, + {965.6481,1283.6045,1283.6045}, + {976.6151,1283.4708,1283.4708}, + {988.1553,1283.4731,1283.4731}, + {1000.2911,1283.4991,1283.4991}, + {1013.0452,1283.2888,1283.2888}, + {1026.4408,1283.2068,1283.2068}, + {1040.502,1282.854,1282.854}, + {1055.2531,1282.8246,1282.8246}, + {1070.7194,1282.4509,1282.4509}, + {1086.9263,1282.1366,1282.1366}, + {1103.9004,1281.6805,1281.6805}, + {1121.6683,1281.3497,1281.3497}, + {1140.2579,1280.9851,1280.9851}, + {1159.6971,1280.6768,1280.6768}, + {1180.0148,1280.2689,1280.2689}, + {1201.2404,1279.3618,1279.3618}, + {1223.4039,1278.7089,1278.7089}, + {1246.5363,1277.9419,1277.9419}, + {1270.6688,1276.0315,1276.0315}, + {1295.8336,1274.8234,1274.8234}, + {1322.0635,1272.7963,1272.7963}, + {1349.3917,1270.1302,1270.1302}, + {1377.8527,1266.1652,1266.1652}, + {1407.4811,1260.8419,1260.8419}, + {1438.3125,1253.3003,1253.3003}, + {1470.3833,1244.5061,1244.5061}, + {1503.7303,1232.5726,1232.5726}, + {1538.3914,1217.3304,1217.3304}, + {1574.4049,1198.2084,1198.2084}, + {1611.8101,1176.7759,1176.7759}, + {1650.6469,1154.4043,1154.4043}, + {1690.9559,1128.3533,1128.3533}, + {1732.7789,1089,1089}, + {1821.1359,1047.5177,1047.5177}, + {1867.7567,1016.2104,1016.2104}, + {1916.0651,984.7769,984.7769}, + {1966.1063,953.2874,953.2874}, + {2017.9265,920.6101,920.6101}, + {2071.573,887.09,887.09}, + {2127.0933,851.7007,851.7007}, + {2184.5361,816.75,816.75}, + {2305.3887,754.0078,754.0078}, + {2368.8997,721.3992,721.3992}, + {2434.5366,689.3527,689.3527}, + {2502.3521,658.8939,658.8939}, + {2572.3999,628.5602,628.5602}, + {2644.7349,599.2983,599.2983}, + {2719.4126,569.1844,569.1844}, + {2796.4893,544.5,544.5}, + {2958.0703,491.2751,491.2751}, + {3042.6919,468.1365,468.1365}, + {3129.9478,446.146,446.146}, + {3219.8982,425.1326,425.1326}, + {3312.6057,405.4332,405.4332}, + {3408.1331,387.0562,387.0562}, + {3506.5439,369.5298,369.5298}, + {3607.9033,353.7877,353.7877}, + {3712.2771,338.264,338.264}, + {3819.7314,324.5506,324.5506}, + {3930.3347,308.7356,308.7356}, + {4044.1553,296.194,296.194}, + {4161.2627,284.466,284.466}, + {4281.728,272.25,272.25}, + {4533.0195,249.2416,249.2416}, + {4663.9917,240.8623,240.8623}, + {4798.6152,231.4884,231.4884}, + {4936.9644,221.9211,221.9211}, + {5079.1172,214.1089,214.1089}, + {5225.1514,206.1059,206.1059}, + {5375.145,199.4312,199.4312}, + {5529.1787,192.4627,192.4627}, + {5687.3335,186.2214,186.2214}, + {5849.6919,179.7628,179.7628}, + {6016.3364,173.8859,173.8859}, + {6187.3521,168.3429,168.3429}, + {6362.8232,162.9014,162.9014}, + {6542.8379,157.5549,157.5549}, + {6727.4824,152.6496,152.6496}, + {6916.8462,147.6369,147.6369}, + {7111.019,143.0052,143.0052}, + {7310.0918,138.6415,138.6415}, + {7514.1567,134.3855,134.3855}, + {7723.3071,130.3516,130.3516}, + {7937.6372,126.2824,126.2824}, + {8157.2432,122.406,122.406}, + {8382.2217,118.8456,118.8456}, + {8612.6699,115.4299,115.4299}, + {8848.6885,111.6104,111.6104}, + {9090.377,108.5394,108.5394}, + {9337.8359,105.2933,105.2933}, + {9591.1699,102.3992,102.3992}, + {9850.4814,99.3358,99.3358}, + {10115.876,96.4839,96.4839}, + {10387.4609,93.7825,93.7825}, + {10665.3428,91.202,91.202}, + {10949.6318,88.5837,88.5837}, + {11240.4365,86.0813,86.0813}, + {11537.8691,83.6826,83.6826}, + {11842.042,81.2935,81.2935}, + {12153.0684,79.0205,79.0205}, + {12471.0654,76.9506,76.9506}, + {12796.1484,75.0336,75.0336}, + {13128.4346,72.9454,72.9454}, + {13468.0439,70.8509,70.8509}, + {13815.0967,69.1639,69.1639}, + {14169.7139,67.2585,67.2585}, + {14532.0195,65.5513,65.5513}, + {14902.1367,63.9257,63.9257}, + {15280.1924,61.706,61.706}, + {15666.3135,60.4764,60.4764}, + {16060.627,58.9538,58.9538}, + {16463.2637,57.8524,57.8524}, + {16874.3535,55.6492,55.6492}, + {17294.0312,54.4416,54.4416}, + {17722.4277,53.0858,53.0858}, + {18159.6816,51.6723,51.6723}, + {18605.9258,50.635,50.635}, + {19061.3008,49.3032,49.3032}, + {19525.9453,47.6384,47.6384}, + {20000,46.83,46.83} + +}; + + #endif //_MEADOWLARKLC_H_ From a101485203d511826e1f9985a3e87e677b1ddeb3 Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Tue, 26 Jul 2022 19:08:13 -0700 Subject: [PATCH 08/29] minor update --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp index 5c0f7e4d1..27e3fbe4f 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp @@ -116,13 +116,13 @@ #include #include #include -#include "usbdrvd.h" #include #include //////// MeadowlarkLC ////////// #include "MeadowlarkLC.h" +#include "usbdrvd.h" #include "resource.h" //////// Micro-manager interface ////////// From 3b8f2e5c5601d495bec3e45cb98aec04f1e25526 Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Wed, 27 Jul 2022 17:01:50 -0700 Subject: [PATCH 09/29] move resource.h to project files --- DeviceAdapters/MeadowlarkLC/resource.h | 22 ++++++++++++++++++++++ 1 file changed, 22 insertions(+) create mode 100644 DeviceAdapters/MeadowlarkLC/resource.h diff --git a/DeviceAdapters/MeadowlarkLC/resource.h b/DeviceAdapters/MeadowlarkLC/resource.h new file mode 100644 index 000000000..efe1f6b90 --- /dev/null +++ b/DeviceAdapters/MeadowlarkLC/resource.h @@ -0,0 +1,22 @@ +//{{NO_DEPENDENCIES}} +// Microsoft Visual C++ generated include file. +// Used by MeadowlarkLC.rc +// +#define TEXTFILE 256 +#define IDR_TEXT1 701 +#define IDR_TEXT2 702 +#define IDR_B14181 703 +#define IDR_B14182 704 +#define IDR_B14183 705 +#define IDR_T001 706 + +// Next default values for new objects +// +#ifdef APSTUDIO_INVOKED +#ifndef APSTUDIO_READONLY_SYMBOLS +#define _APS_NEXT_RESOURCE_VALUE 141 +#define _APS_NEXT_COMMAND_VALUE 40001 +#define _APS_NEXT_CONTROL_VALUE 1001 +#define _APS_NEXT_SYMED_VALUE 104 +#endif +#endif From 5f6c9667119bfb384bb2cc3fe17c97dd1ba84f4b Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Tue, 2 Aug 2022 15:58:23 -0700 Subject: [PATCH 10/29] Update library locations locations --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj index ffc8baf63..c046a93da 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj @@ -11,6 +11,7 @@ + @@ -60,13 +61,13 @@ true - "$(MM_3RDPARTYPRIVATE)\Meadowlark\V104\lib64";$(LibraryPath) - $(MM_3RDPARTYPRIVATE)\Meadowlark\V104\include;$(IncludePath) + "$(MM_3RDPARTYPRIVATE)\Meadowlark\V107\lib64";$(LibraryPath) + $(MM_3RDPARTYPRIVATE)\Meadowlark\V107\include;$(IncludePath) false - "$(MM_3RDPARTYPRIVATE)\Meadowlark\V104\lib64";$(LibraryPath) - $(MM_3RDPARTYPRIVATE)\Meadowlark\V104\include;$(IncludePath) + "$(MM_3RDPARTYPRIVATE)\Meadowlark\V107\lib64";$(LibraryPath) + $(MM_3RDPARTYPRIVATE)\Meadowlark\V107\include;$(IncludePath) @@ -77,7 +78,7 @@ Windows true - usbdrvd64.lib;%(AdditionalDependencies) + usbdrvd.lib;%(AdditionalDependencies) false @@ -94,7 +95,7 @@ true true true - usbdrvd64.lib;%(AdditionalDependencies) + usbdrvd.lib;%(AdditionalDependencies) false From 3c140a6d3196c2a43d4815820e6b7ea118035598 Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Tue, 2 Aug 2022 17:30:05 -0700 Subject: [PATCH 11/29] Change dev adapter name --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj | 1 + 1 file changed, 1 insertion(+) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj index c046a93da..ba0f186cf 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj @@ -28,6 +28,7 @@ {bd7b178b-b026-48fc-b7bd-c5d5257b3a20} MeadowlarkLC 10.0 + MeadowlarkLcOpenSource From fd269d5fca01edeb8c2cec280995cf76d43a900e Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Tue, 2 Aug 2022 17:30:13 -0700 Subject: [PATCH 12/29] Revert "Update library locations locations" This reverts commit 5f6c9667119bfb384bb2cc3fe17c97dd1ba84f4b. --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj | 13 ++++++------- 1 file changed, 6 insertions(+), 7 deletions(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj index ba0f186cf..0b8b5a616 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj @@ -11,7 +11,6 @@ - @@ -62,13 +61,13 @@ true - "$(MM_3RDPARTYPRIVATE)\Meadowlark\V107\lib64";$(LibraryPath) - $(MM_3RDPARTYPRIVATE)\Meadowlark\V107\include;$(IncludePath) + "$(MM_3RDPARTYPRIVATE)\Meadowlark\V104\lib64";$(LibraryPath) + $(MM_3RDPARTYPRIVATE)\Meadowlark\V104\include;$(IncludePath) false - "$(MM_3RDPARTYPRIVATE)\Meadowlark\V107\lib64";$(LibraryPath) - $(MM_3RDPARTYPRIVATE)\Meadowlark\V107\include;$(IncludePath) + "$(MM_3RDPARTYPRIVATE)\Meadowlark\V104\lib64";$(LibraryPath) + $(MM_3RDPARTYPRIVATE)\Meadowlark\V104\include;$(IncludePath) @@ -79,7 +78,7 @@ Windows true - usbdrvd.lib;%(AdditionalDependencies) + usbdrvd64.lib;%(AdditionalDependencies) false @@ -96,7 +95,7 @@ true true true - usbdrvd.lib;%(AdditionalDependencies) + usbdrvd64.lib;%(AdditionalDependencies) false From 40518fefef1be6a8f0c1bafe70b56704b66f66b6 Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Wed, 3 Aug 2022 09:03:22 -0700 Subject: [PATCH 13/29] Revert "Change dev adapter name" This reverts commit 3c140a6d3196c2a43d4815820e6b7ea118035598. --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj | 1 - 1 file changed, 1 deletion(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj index 0b8b5a616..ffc8baf63 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj @@ -27,7 +27,6 @@ {bd7b178b-b026-48fc-b7bd-c5d5257b3a20} MeadowlarkLC 10.0 - MeadowlarkLcOpenSource From a51724464dc1199d1d456db1734647d970d049f8 Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Wed, 3 Aug 2022 10:15:15 -0700 Subject: [PATCH 14/29] Change dev adapter name --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp | 2 +- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj | 9 +++++---- 2 files changed, 6 insertions(+), 5 deletions(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp index 27e3fbe4f..c901b965b 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp @@ -130,7 +130,7 @@ ////////////////////////////////////////////////////////////////////////////////////////// -const char* g_ControllerName = "MeadowlarkLC"; +const char* g_ControllerName = "MeadowlarkLcOpenSource"; const char* g_ControllerAbout = "MeadowlarkLC Digital Device Controller/Interface"; const char* g_ControllerDevices = "Select Device #"; const char* g_ControllerDeviceType = "Select Device Interface"; diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj index ffc8baf63..ab3e548fc 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj @@ -27,6 +27,7 @@ {bd7b178b-b026-48fc-b7bd-c5d5257b3a20} MeadowlarkLC 10.0 + MeadowlarkLcOpenSource @@ -60,12 +61,12 @@ true - "$(MM_3RDPARTYPRIVATE)\Meadowlark\V104\lib64";$(LibraryPath) + "$(MM_3RDPARTYPRIVATE)\Meadowlark\V104\lib64";$(LibraryPath) $(MM_3RDPARTYPRIVATE)\Meadowlark\V104\include;$(IncludePath) false - "$(MM_3RDPARTYPRIVATE)\Meadowlark\V104\lib64";$(LibraryPath) + "$(MM_3RDPARTYPRIVATE)\Meadowlark\V104\lib64";$(LibraryPath) $(MM_3RDPARTYPRIVATE)\Meadowlark\V104\include;$(IncludePath) @@ -77,7 +78,7 @@ Windows true - usbdrvd64.lib;%(AdditionalDependencies) + usbdrvd64.lib;%(AdditionalDependencies) false @@ -94,7 +95,7 @@ true true true - usbdrvd64.lib;%(AdditionalDependencies) + usbdrvd64.lib;%(AdditionalDependencies) false From 89af8c942938b71c88f34125170df31440aa7bc6 Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Wed, 16 Nov 2022 12:25:16 -0800 Subject: [PATCH 15/29] Update to MLO v1.07 driver --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj index ab3e548fc..73e4f8f81 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj @@ -61,13 +61,13 @@ true - "$(MM_3RDPARTYPRIVATE)\Meadowlark\V104\lib64";$(LibraryPath) - $(MM_3RDPARTYPRIVATE)\Meadowlark\V104\include;$(IncludePath) + "$(MM_3RDPARTYPRIVATE)\Meadowlark\V107\lib64";$(LibraryPath) + $(MM_3RDPARTYPRIVATE)\Meadowlark\V107\include;$(IncludePath) false - "$(MM_3RDPARTYPRIVATE)\Meadowlark\V104\lib64";$(LibraryPath) - $(MM_3RDPARTYPRIVATE)\Meadowlark\V104\include;$(IncludePath) + "$(MM_3RDPARTYPRIVATE)\Meadowlark\V107\lib64";$(LibraryPath) + $(MM_3RDPARTYPRIVATE)\Meadowlark\V107\include;$(IncludePath) @@ -78,7 +78,7 @@ Windows true - usbdrvd64.lib;%(AdditionalDependencies) + usbdrvd.lib;%(AdditionalDependencies) false @@ -95,7 +95,7 @@ true true true - usbdrvd64.lib;%(AdditionalDependencies) + usbdrvd.lib;%(AdditionalDependencies) false From 66b5ef335a240a81513d3890d9b4fd6970f3b46c Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Mon, 30 Jan 2023 17:41:46 -0800 Subject: [PATCH 16/29] Create license.txt --- DeviceAdapters/MeadowlarkLC/license.txt | 29 +++++++++++++++++++++++++ 1 file changed, 29 insertions(+) create mode 100644 DeviceAdapters/MeadowlarkLC/license.txt diff --git a/DeviceAdapters/MeadowlarkLC/license.txt b/DeviceAdapters/MeadowlarkLC/license.txt new file mode 100644 index 000000000..52d46edac --- /dev/null +++ b/DeviceAdapters/MeadowlarkLC/license.txt @@ -0,0 +1,29 @@ +BSD 3-Clause License + +Copyright (c) 2023, Mehta Laboratory (Computational Microscopy), CZ Biohub +All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: + +1. Redistributions of source code must retain the above copyright notice, this + list of conditions and the following disclaimer. + +2. Redistributions in binary form must reproduce the above copyright notice, + this list of conditions and the following disclaimer in the documentation + and/or other materials provided with the distribution. + +3. Neither the name of the copyright holder nor the names of its + contributors may be used to endorse or promote products derived from + this software without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE +FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR +SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER +CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, +OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. From 718740bb95f128e9a64a90afebdc9261eaaf1f1c Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Tue, 7 Feb 2023 16:04:58 -0800 Subject: [PATCH 17/29] build with v108 usb driver --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj index 73e4f8f81..a8c4b1da9 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj @@ -61,13 +61,13 @@ true - "$(MM_3RDPARTYPRIVATE)\Meadowlark\V107\lib64";$(LibraryPath) - $(MM_3RDPARTYPRIVATE)\Meadowlark\V107\include;$(IncludePath) + "$(MM_3RDPARTYPRIVATE)\Meadowlark\V108\64 bit";$(LibraryPath) + $(MM_3RDPARTYPRIVATE)\Meadowlark\V108\64 bit;$(IncludePath) false - "$(MM_3RDPARTYPRIVATE)\Meadowlark\V107\lib64";$(LibraryPath) - $(MM_3RDPARTYPRIVATE)\Meadowlark\V107\include;$(IncludePath) + "$(MM_3RDPARTYPRIVATE)\Meadowlark\V108\64 bit";$(LibraryPath) + $(MM_3RDPARTYPRIVATE)\Meadowlark\V108\64 bit;$(IncludePath) From b96afaf937b246b35b1a42a85f8aad08f46e6fbd Mon Sep 17 00:00:00 2001 From: Shalin Mehta Date: Mon, 3 Apr 2023 16:57:30 -0700 Subject: [PATCH 18/29] Update MeadowlarkLC license.txt --- DeviceAdapters/MeadowlarkLC/license.txt | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/DeviceAdapters/MeadowlarkLC/license.txt b/DeviceAdapters/MeadowlarkLC/license.txt index 52d46edac..550b9e575 100644 --- a/DeviceAdapters/MeadowlarkLC/license.txt +++ b/DeviceAdapters/MeadowlarkLC/license.txt @@ -1,6 +1,7 @@ BSD 3-Clause License - -Copyright (c) 2023, Mehta Laboratory (Computational Microscopy), CZ Biohub +Copyright (c) +Marine Biological Laboratory (2011 - 2017) +Chan Zuckerberg Biohub San Francisco (2017 - 2023) All rights reserved. Redistribution and use in source and binary forms, with or without From a2992fa628a23fd2f1cd4f71e2cb1f6401c2d437 Mon Sep 17 00:00:00 2001 From: Eduardo Hirata Date: Mon, 3 Apr 2023 17:54:40 -0700 Subject: [PATCH 19/29] Merge branch 'MeadowlarkLC_v107' of https://github.com/mehta-lab/mmCoreAndDevices into MeadowlarkLC_v107 --- DeviceAdapters/MeadowlarkLC/license.txt | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/DeviceAdapters/MeadowlarkLC/license.txt b/DeviceAdapters/MeadowlarkLC/license.txt index 52d46edac..550b9e575 100644 --- a/DeviceAdapters/MeadowlarkLC/license.txt +++ b/DeviceAdapters/MeadowlarkLC/license.txt @@ -1,6 +1,7 @@ BSD 3-Clause License - -Copyright (c) 2023, Mehta Laboratory (Computational Microscopy), CZ Biohub +Copyright (c) +Marine Biological Laboratory (2011 - 2017) +Chan Zuckerberg Biohub San Francisco (2017 - 2023) All rights reserved. Redistribution and use in source and binary forms, with or without From 37063e8adc26fbc3ba62d2833ea0f3e862e1ca08 Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Mon, 3 Apr 2023 18:21:27 -0700 Subject: [PATCH 20/29] rename to MeadowlarkLC fixes #3 --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj index a8c4b1da9..ed01c6d4a 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj @@ -27,7 +27,7 @@ {bd7b178b-b026-48fc-b7bd-c5d5257b3a20} MeadowlarkLC 10.0 - MeadowlarkLcOpenSource + MeadowlarkLC From 107de093d7210fe36f151dc833d4dfd54697f72a Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Mon, 3 Apr 2023 18:34:17 -0700 Subject: [PATCH 21/29] update preamble fixes #4 --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp | 109 +++---------------- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h | 39 +++---- 2 files changed, 28 insertions(+), 120 deletions(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp index 2dec702b2..1bfbf3439 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp @@ -3,105 +3,24 @@ // PROJECT: Micro-Manager // SUBSYSTEM: DeviceAdapters //----------------------------------------------------------------------------- -// DESCRIPTION: MeadowlarkLC Device Adapter for Meadowlark Optics liquid crystal controllers -// -// Copyright � 2009 - 2018, Marine Biological Laboratory +// DESCRIPTION: MeadowlarkLC Device Adapter for Meadowlark Optics D5020 liquid crystal controller // -// LICENSE (Berkeley Software Distribution License): Redistribution and use in source and binary forms, -// with or without modification, are permitted provided that the following conditions are met: -// -// 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. -// 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer -// in the documentation and/or other materials provided with the distribution. -// 3. Neither the name of the Marine Biological Laboratory nor the names of its contributors may be used to endorse or promote products -// derived from this software without specific prior written permission. -// -// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE -// COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES -// (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -// HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) -// ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -// -// The views and conclusions contained in the software and documentation are those of the authors and should not be interpreted as -// representing official policies, either expressed or implied, of any organization. -// -// Developed at the Laboratory of Rudolf Oldenbourg at the Marine Biological Laboratory in Woods Hole, MA. -// LAST UPDATE: Ivan Ivanov, Chan Zuckerberg Biohub - June, 2022 -// -// -// AUTHOR: Amitabh Verma, MBL - Dec. 05, 2012 -// -// ToDo List at EOF -// -// Change Log - Ivan Ivanov - June 29, 2022 - 1.1.0 -// 1. Updated VS project files to allow compiling the device adapter along with MicroManager nightly builds. -// 2. Fixed bug in OnVoltage function. Function input and output are now both in units of volts. -// 3. Updated OnRetardance function to refresh the LC retardance once LC voltage is set. Similarly for OnVoltage. -// 4. Renamed "Version Number" property to "Controller Serial Number", which is more accurate. +// AUTHOR: Amitabh Verma +// Ivan Ivanov // -// Change Log - Amitabh Verma - Aug. 21, 2018 - 1.00.03 -// 1. Implemented config file for device adapter that gets written out when not found based on serial number of device. -// This config file can be updated with palette element values for different wavelengths and can be set using command eg. "sp 546" -// The first defined palette in the csv file is loaded as default at startup when the device driver is loaded. -// -// Change Log - Amitabh Verma - Aug. 06, 2018 - 1.00.02 -// 1. Option for LC - File (Serial_No.csv) -// Note: This method will allow providing LCs with individual custom calibration curves and also allow multiple instances of the adapter to -// load individual calibration curves based on the device Serial No. -// -// Change Log - Amitabh Verma - Oct. 10, 2014 -// 1. Option for LC - Loaded From File (mmgr_dal_MeadowlarkLC.csv) -// Note: This method will allow providing LCs with custom calibration curve and no further need to recompile this device adapter -// with additional calibration curves. -// -// Change Log - Amitabh Verma - July. 24, 2014 -// 1. Replaced ',' comma with ';' semi-colon in property names due to Micro-Manager warning during HW Config Wizard 'Contains reserved chars' -// Note: This will break Pol-Acquisition (OpenPolScope) and requires compatible version which uses same name for Property -// -// Change Log -// March 19, 2014 -// 1. Absolute retardance field -// 2. Extended retardance range to minimum based on voltage and maximum 1.6 waves -// 3. changedTime_ is called only when setting voltage - not for other operations -// -// Feb. 10, 2014 -// 1. Added support for D5020 (20V) Controller. Tested with actual unit. -// - Set Max no. of LC based on controller type. -// - Check for no. of Active LCs less than Max -// -// Nov. 21, 2013 -// 1. Calibration curves now part of dll and embedded as resource -// - To add more curves add in resource.h and MeadownlarkLC.rc and then add selection case for LC Type and under Initialize() -// -// Nov. 19, 2013 -// 1. Added LC Calibration curve selection option -// -// Nov. 18, 2013 -// 1. Added scaling based of Controller type (D3050, D3060HV, D5020) -// -// Nov. 14, 2013 -// 1. Support for 20V controller - untested (D5020) -// 2. Added TNE support with defaults 20ms pluse duration with 10V/20V Amplitude -// 3. Added Exercise LC Code -// 4a. Added characterization for 10V and 20V range device -// 4b. Implemented range for Voltage and Retardance based on 10V/20V device -// -// June 27, 2013 -// 1. Load calibration curves via csv file -// 2. Generate interpolated calibration curves -// 3. Export calibration curve being used -// -// June 23, 2013 -// 1. MeadowlarkLC beta release version 1.0 -// -// Apr. 23, 2013 -// 1. MeadowlarkLC alpha release version 1.0 +// COPYRIGHT: Marine Biological Laboratory (2011 - 2017) +// Chan Zuckerberg Biohub San Francisco (2017 - 2023) +// +// LICENSE: This file is distributed under the BSD license. +// License text is included with the source distribution. // -// Dec. 05, 2012 -// 1. Implementing MeadowlarkLC from VariLC device adapter +// 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. // -// http://stackoverflow.com/questions/4200189/how-to-use-cmake-to-generate-vs-project-which-link-to-some-dll-files +// IN NO EVENT SHALL THE COPYRIGHT OWNER OR +// CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, +// INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES. #ifdef WIN32 diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h index 032f13aa7..be7e0bda1 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h @@ -3,35 +3,24 @@ // PROJECT: Micro-Manager // SUBSYSTEM: DeviceAdapters //----------------------------------------------------------------------------- -// DESCRIPTION: MeadowlarkLC Device Adapter for Meadowlark Optics liquid crystal controllers +// DESCRIPTION: MeadowlarkLC Device Adapter for Meadowlark Optics D5020 liquid crystal controller // -// Copyright � 2009 - 2014, Marine Biological Laboratory +// AUTHOR: Amitabh Verma +// Ivan Ivanov // -// LICENSE (Berkeley Software Distribution License): Redistribution and use in source and binary forms, -// with or without modification, are permitted provided that the following conditions are met: -// -// 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. -// 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer -// in the documentation and/or other materials provided with the distribution. -// 3. Neither the name of the Marine Biological Laboratory nor the names of its contributors may be used to endorse or promote products -// derived from this software without specific prior written permission. -// -// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE -// COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES -// (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -// HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) -// ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -// -// The views and conclusions contained in the software and documentation are those of the authors and should not be interpreted as -// representing official policies, either expressed or implied, of any organization. -// -// Developed at the Laboratory of Rudolf Oldenbourg at the Marine Biological Laboratory in Woods Hole, MA. -// +// COPYRIGHT: Marine Biological Laboratory (2011 - 2017) +// Chan Zuckerberg Biohub San Francisco (2017 - 2023) +// +// LICENSE: This file is distributed under the BSD license. +// License text is included with the source distribution. // -// AUTHOR: Amitabh Verma +// 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. // -// Notes: Refer MeadowlarkLC.cpp for ChangeLog, ToDo and other information +// IN NO EVENT SHALL THE COPYRIGHT OWNER OR +// CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, +// INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES. #ifndef _MEADOWLARKLC_H_ #define _MEADOWLARKLC_H_ From 5496ecc017c31580d569a6e5f19a344d0f1a5b20 Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Mon, 3 Apr 2023 18:45:04 -0700 Subject: [PATCH 22/29] change device name and info --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp | 18 +++--------------- 1 file changed, 3 insertions(+), 15 deletions(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp index 1bfbf3439..34b09951a 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp @@ -49,8 +49,8 @@ ////////////////////////////////////////////////////////////////////////////////////////// -const char* g_ControllerName = "MeadowlarkLcOpenSource"; -const char* g_ControllerAbout = "MeadowlarkLC Digital Device Controller/Interface"; +const char* g_ControllerName = "MeadowlarkLC"; +const char* g_ControllerAbout = "Meadowlark Optics D5020 Liquid Crystal Controller"; const char* g_ControllerDevices = "Select Device #"; const char* g_ControllerDeviceType = "Select Device Interface"; const char* g_ControllerDeviceType10V = "10V (D3050) Controller"; @@ -97,9 +97,8 @@ const char* g_ControllerLCType_B14183_Curves = "CURVE_IDR_B14183"; const char* g_ControllerDescription = "Description"; const char* g_ControllerDescriptionInfo = "Description Info"; const std::string g_Nonedetected = "None detected"; -const LPCSTR g_About = "MeadowlarkLC Device Adapter for Micro-Manager and use with OpenPolScope Micro-Manager plugin. \n Please refer to http://www.openpolscope.org for more information."; -const char* g_Dev_Adapter_Ver = "1.1.0"; +const char* g_Dev_Adapter_Ver = "2.0.0"; using namespace std; const HMODULE GetCurrentModule() @@ -1473,18 +1472,7 @@ int MeadowlarkLC::OnSendToMeadowlarkLC(MM::PropertyBase* pProp, MM::ActionType e SetProperty(propstring.c_str(), description_.c_str()); } - //else if (!searchQuestionMark && ((sendToMeadowlarkLC_ == "About") || sendToMeadowlarkLC_ == "about")) { - // MessageBox(0, g_About, "About", 0); - // SetProperty(propstring.c_str(), description_.c_str()); - - //} - //else if (!searchQuestionMark && ((sendToMeadowlarkLC_ == "Help") || sendToMeadowlarkLC_ == "help")) { - - // MessageBox(0, g_About, "About", 0); - // SetProperty(propstring.c_str(), description_.c_str()); - - //} else if (!searchQuestionMark && ((sendToMeadowlarkLC_ == "import") || sendToMeadowlarkLC_ == "IMPORT")) { loadDefault(); From 8fd923803e5979651ec39120517da4646fe6f8c2 Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Mon, 3 Apr 2023 19:07:31 -0700 Subject: [PATCH 23/29] remove activation key --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp | 28 -------------------- 1 file changed, 28 deletions(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp index 34b09951a..372366d5f 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp @@ -164,7 +164,6 @@ MeadowlarkLC::MeadowlarkLC() : RetToVoltageFactor(0), wavelength_(546.0), // the cached value numberofCurves(1), // default is 1, will change based on import - activationKey_("OPS-MeadowlarkLcOpenSource"), ArrayLength2(198) { @@ -183,7 +182,6 @@ MeadowlarkLC::MeadowlarkLC() : SetErrorText(ERR_INVALID_DEVICE, "The selected plugin does not fit for the device."); SetErrorText(ERR_INVALID_SERIAL_NUMBER, "Invalid Serial Number. Please refer to your Meadowlark device unit."); SetErrorText(ERR_INVALID_LCSERIAL_NUMBER, "Invalid LC-Serial Number. Calibration curve for this LC does not exist."); - SetErrorText(ERR_INVALID_ACTIVATION_KEY, "Invalid Activation Key. Please refer to your Meadowlark device unit."); SetErrorText(ERR_INVALID_LC_UNPAIRED, "Invalid LC-Controller Pair. This Controller is not paired with an LC. Enter LC-S/N"); if (controllerLCType_ == g_ControllerLCType_F002) { SetErrorText(ERR_INVALID_LC_FILE, ".csv File Invalid Selection. The calibration curve file does not exist or is invalid."); @@ -291,9 +289,6 @@ MeadowlarkLC::MeadowlarkLC() : pAct = new CPropertyAction(this, &MeadowlarkLC::OnSerialNumber); CreateProperty("Controller S/N", "Undefined", MM::String, false, pAct, true); - pAct = new CPropertyAction(this, &MeadowlarkLC::OnActivationKey); - CreateProperty("Controller S/N-Activation Key", "Undefined", MM::String, true, pAct, true); - pAct = new CPropertyAction(this, &MeadowlarkLC::OnNumTotalLCs); CreateProperty(g_ControllerTotalLCs, "0", MM::Integer, true, pAct, true); @@ -333,11 +328,6 @@ int MeadowlarkLC::Initialize() return ERR_INVALID_SERIAL_NUMBER; } - setSystemSpecificActivationKey(serialnum_); - if (activationKey_ == "Undefined" || activationKey_ == "" || activationKey_ != SystemSpecificActivationKey) { - return ERR_INVALID_ACTIVATION_KEY; - } - if (controllerLCType_ == g_ControllerLCType_Internal) { return ERR_INVALID_LC_SELECTION; } @@ -1057,19 +1047,6 @@ int MeadowlarkLC::OnDevAdapterVersionNumber(MM::PropertyBase* pProp, MM::ActionT return DEVICE_OK; } -int MeadowlarkLC::OnActivationKey(MM::PropertyBase* pProp, MM::ActionType eAct) -{ - if (eAct == MM::BeforeGet) - { - pProp->Set(activationKey_.c_str()); - } - else if (eAct == MM::AfterSet) - { - pProp->Get(activationKey_); - } - return DEVICE_OK; -} - int MeadowlarkLC::OnControllerType(MM::PropertyBase* pProp, MM::ActionType eAct) { if (eAct == MM::BeforeGet) @@ -2583,11 +2560,6 @@ void MeadowlarkLC::loadResource(int ID) { } } -void MeadowlarkLC::setSystemSpecificActivationKey(std::string serialNum) { - SystemSpecificActivationKey = "OPS-MeadowlarkLcOpenSource"; -} - - //////////////// ---- ToDo ---- ////////////////// // // 1. Added Exercise routine in a new thread so that it does not stop device interface From 05505d0b74b2feb778d452c06d8bed168a4f66b5 Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Tue, 4 Apr 2023 11:10:56 -0700 Subject: [PATCH 24/29] remove support for old LC controllers, fixes#6 --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp | 146 +++---------------- 1 file changed, 23 insertions(+), 123 deletions(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp index 372366d5f..6bf8ed835 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp @@ -53,12 +53,10 @@ const char* g_ControllerName = "MeadowlarkLC"; const char* g_ControllerAbout = "Meadowlark Optics D5020 Liquid Crystal Controller"; const char* g_ControllerDevices = "Select Device #"; const char* g_ControllerDeviceType = "Select Device Interface"; -const char* g_ControllerDeviceType10V = "10V (D3050) Controller"; -const char* g_ControllerDeviceType20V_D3060HV = "20V (D3060HV) Controller"; -const char* g_ControllerDeviceType20V_D5020 = "20V (D5020) Controller"; -const double g_ControllerDeviceType10VFac = 6553.5; +const char* g_ControllerDeviceType10V_D5020 = "D5020 Controller (untested)"; +const char* g_ControllerDeviceType20V_D5020 = "D5020-20V Controller"; +const double g_ControllerDeviceType10VFac_D5020 = 1000; const double g_ControllerDeviceType20VFac_D5020 = 1000; -const double g_ControllerDeviceType20VFac_D3060HV = 655.35; const char* g_ControllerTotalLCs = "Total Number of LCs"; const double g_ControllerDeviceRetardanceLowLimit = 0.001; @@ -68,31 +66,10 @@ const double g_ControllerDeviceRetardanceAbsRetLow = 0.0; const double g_ControllerDeviceRetardanceAbsRetHigh = 1200.0; const char* g_ControllerLCType_Internal = "Internal (Single generic 546nm curve)"; -const char* g_ControllerLCType_Paired = "Use LC Paired with Controller"; const char* g_ControllerLCType_F001 = "File (mmgr_dal_MeadowlarkLC.csv)"; //"Loaded From File (mmgr_dal_MeadowlarkLC.csv)"; -const char* g_ControllerLCType_F001b = "Loaded From File (mmgr_dal_MeadowlarkLC.csv)"; // retained for backward compatibility -const char* g_ControllerLCType_F002 = "File (SERIAL_NO.csv)"; //"Loaded From File (SERIAL_NO.csv)"; -const char* g_ControllerLCType_B001 = "B001 (Non-Bonded)"; //"Non-Bonded LC Type"; -const char* g_ControllerLCType_B002 = "B002 (Bonded)"; // "Bonded LC Type"; -const char* g_ControllerLCType_T001 = "Thick 001 (Bonded)"; // "Thick Bonded LC Type"; - -const char* g_ControllerLCType_B14181 = "B14181"; // "Bonded LC Type"; // L13009 -const char* g_ControllerSN_L13009 = "L13009"; // "Bonded LC Type"; // B14181 (A14001 & B14022) - -const char* g_ControllerLCType_B14182 = "B14182"; // "Bonded LC Type"; // L13010 -const char* g_ControllerSN_L13010 = "L13010"; // "Bonded LC Type"; // B14182 (A14004 & B14021) - -const char* g_ControllerLCType_B14183 = "B14183"; // "Bonded LC Type"; // L13011 -const char* g_ControllerSN_L13011 = "L13011"; // "Bonded LC Type"; // B14183 (A14004 & A14006) const char* g_ControllerLCType_F001_Curves = "mmgr_dal_MeadowlarkLC.csv"; const char* g_ControllerLCType_F002_Curves = ".csv"; -const char* g_ControllerLCType_1_Curves = "CURVE_IDR_0_1"; -const char* g_ControllerLCType_2_Curves = "CURVE_IDR_0_2"; -const char* g_ControllerLCType_T001_Curves = "CURVE_IDR_T001"; -const char* g_ControllerLCType_B14181_Curves = "CURVE_IDR_B14181"; -const char* g_ControllerLCType_B14182_Curves = "CURVE_IDR_B14182"; -const char* g_ControllerLCType_B14183_Curves = "CURVE_IDR_B14183"; const char* g_ControllerDescription = "Description"; const char* g_ControllerDescriptionInfo = "Description Info"; @@ -168,8 +145,8 @@ MeadowlarkLC::MeadowlarkLC() : { cur_dev = 0; - controllerType_ = g_ControllerDeviceType20V_D5020; // default to D5020 - controllerLCType_ = g_ControllerLCType_F002; // USE FILE.csv by Default + controllerType_ = g_ControllerDeviceType20V_D5020; // default to D5020-20V + controllerLCType_ = g_ControllerLCType_F001; // use mmgr_dal_MeadowlarkLC.csv file by default description_ = "Not found"; serialnum_ = "Undefined"; cur_dev_name = "1"; @@ -183,12 +160,7 @@ MeadowlarkLC::MeadowlarkLC() : SetErrorText(ERR_INVALID_SERIAL_NUMBER, "Invalid Serial Number. Please refer to your Meadowlark device unit."); SetErrorText(ERR_INVALID_LCSERIAL_NUMBER, "Invalid LC-Serial Number. Calibration curve for this LC does not exist."); SetErrorText(ERR_INVALID_LC_UNPAIRED, "Invalid LC-Controller Pair. This Controller is not paired with an LC. Enter LC-S/N"); - if (controllerLCType_ == g_ControllerLCType_F002) { - SetErrorText(ERR_INVALID_LC_FILE, ".csv File Invalid Selection. The calibration curve file does not exist or is invalid."); - } - else { - SetErrorText(ERR_INVALID_LC_SELECTION, "Invalid Selection. The calibration curve file (mmgr_dal_MeadowlarkLC.csv) does not exist or is invalid."); - } + SetErrorText(ERR_INVALID_LC_SELECTION, "Invalid Selection. The calibration curve file (mmgr_dal_MeadowlarkLC.csv) does not exist or is invalid."); std::string str = IntToString(numTotalLCs_).c_str(); totalLCsMsg = "Invalid Active LCs. Number of Active LCs cannot be more than Total of " + str + " LCs"; @@ -267,24 +239,16 @@ MeadowlarkLC::MeadowlarkLC() : // LC Controller Type pAct = new CPropertyAction(this, &MeadowlarkLC::OnControllerType); - CreateProperty(g_ControllerDeviceType, g_ControllerDeviceType10V, MM::String, false, pAct, true); - AddAllowedValue(g_ControllerDeviceType, g_ControllerDeviceType10V); - AddAllowedValue(g_ControllerDeviceType, g_ControllerDeviceType20V_D3060HV); + CreateProperty(g_ControllerDeviceType, g_ControllerDeviceType20V_D5020, MM::String, false, pAct, true); AddAllowedValue(g_ControllerDeviceType, g_ControllerDeviceType20V_D5020); + //AddAllowedValue(g_ControllerDeviceType, g_ControllerDeviceType10V_D5020); // LC (Non-Bonded, Bonded, etc...) pAct = new CPropertyAction(this, &MeadowlarkLC::OnControllerLCType); - CreateProperty("Select LC Type", g_ControllerLCType_Paired, MM::String, false, pAct, true); - AddAllowedValue("Select LC Type", g_ControllerLCType_Paired); - AddAllowedValue("Select LC Type", g_ControllerLCType_B001); - AddAllowedValue("Select LC Type", g_ControllerLCType_B002); - AddAllowedValue("Select LC Type", g_ControllerLCType_B14181); - AddAllowedValue("Select LC Type", g_ControllerLCType_B14182); - AddAllowedValue("Select LC Type", g_ControllerLCType_B14183); - AddAllowedValue("Select LC Type", g_ControllerLCType_T001); + CreateProperty("Select LC Type", g_ControllerLCType_F001, MM::String, false, pAct, true); AddAllowedValue("Select LC Type", g_ControllerLCType_F001); - AddAllowedValue("Select LC Type", g_ControllerLCType_F001b); - AddAllowedValue("Select LC Type", g_ControllerLCType_F002); + //AddAllowedValue("Select LC Type", g_ControllerLCType_Internal); + pAct = new CPropertyAction(this, &MeadowlarkLC::OnSerialNumber); CreateProperty("Controller S/N", "Undefined", MM::String, false, pAct, true); @@ -328,27 +292,11 @@ int MeadowlarkLC::Initialize() return ERR_INVALID_SERIAL_NUMBER; } + // Why do we raise an error here? if (controllerLCType_ == g_ControllerLCType_Internal) { return ERR_INVALID_LC_SELECTION; } - if (controllerLCType_ == g_ControllerLCType_Paired) { - if (serialnum_ == g_ControllerSN_L13009) { - controllerLCType_ = g_ControllerLCType_B14181; - - } - else if (serialnum_ == g_ControllerSN_L13010) { - controllerLCType_ = g_ControllerLCType_B14182; - - } - else if (serialnum_ == g_ControllerSN_L13011) { - controllerLCType_ = g_ControllerLCType_B14183; - - } - if (controllerLCType_ == g_ControllerLCType_Paired) { - return ERR_INVALID_LC_UNPAIRED; - } - } if (controllerLCType_ == "Undefined" || controllerLCType_ == "") { return ERR_INVALID_LCSERIAL_NUMBER; } @@ -383,17 +331,13 @@ int MeadowlarkLC::Initialize() palEl_[i] = DoubleToString(wavelength_) + str; } - if (controllerType_ == g_ControllerDeviceType10V) { - g_ControllerDeviceTypeVFac = g_ControllerDeviceType10VFac; - tneAmplitude_ = 10; - } - else if (controllerType_ == g_ControllerDeviceType20V_D5020) { + if (controllerType_ == g_ControllerDeviceType20V_D5020) { g_ControllerDeviceTypeVFac = g_ControllerDeviceType20VFac_D5020; tneAmplitude_ = 20; } - else if (controllerType_ == g_ControllerDeviceType20V_D3060HV) { - g_ControllerDeviceTypeVFac = g_ControllerDeviceType20VFac_D3060HV; - tneAmplitude_ = 20; + else if (controllerType_ == g_ControllerDeviceType10V_D5020) { + g_ControllerDeviceTypeVFac = g_ControllerDeviceType10VFac_D5020; + tneAmplitude_ = 10; } // load curve based on LC Type @@ -444,16 +388,7 @@ int MeadowlarkLC::Initialize() // Controller LC Type pAct = new CPropertyAction(this, &MeadowlarkLC::OnControllerLCType); ret = CreateProperty("Controller LC Type", controllerLCType_.c_str(), MM::String, false, pAct); - AddAllowedValue("Controller LC Type", g_ControllerLCType_Paired); - AddAllowedValue("Controller LC Type", g_ControllerLCType_B001); - AddAllowedValue("Controller LC Type", g_ControllerLCType_B002); - AddAllowedValue("Controller LC Type", g_ControllerLCType_B14181); - AddAllowedValue("Controller LC Type", g_ControllerLCType_B14182); - AddAllowedValue("Controller LC Type", g_ControllerLCType_B14183); - AddAllowedValue("Controller LC Type", g_ControllerLCType_T001); AddAllowedValue("Controller LC Type", g_ControllerLCType_F001); - AddAllowedValue("Controller LC Type", g_ControllerLCType_F001b); - AddAllowedValue("Controller LC Type", g_ControllerLCType_F002); AddAllowedValue("Controller LC Type", g_ControllerLCType_Internal); if (ret != DEVICE_OK) return ret; @@ -519,7 +454,7 @@ int MeadowlarkLC::Initialize() pActX = new CPropertyActionEx(this, &MeadowlarkLC::OnVoltage, i); CreateProperty(s.str().c_str(), "7.500", MM::Float, false, pActX); - if (controllerType_ == g_ControllerDeviceType10V) { + if (controllerType_ == g_ControllerDeviceType10V_D5020) { SetPropertyLimits(s.str().c_str(), 0, 10.0); } else { @@ -815,7 +750,7 @@ int MeadowlarkLC::OnRetardance(MM::PropertyBase* pProp, MM::ActionType eAct, lon double voltage = GetVoltage(index); // in mV //double voltage = voltage_[index]; double maxV = 10000; - if (controllerType_ == g_ControllerDeviceType20V_D3060HV || controllerType_ == g_ControllerDeviceType20V_D5020) { + if (controllerType_ == g_ControllerDeviceType20V_D5020) { maxV = 20000; } @@ -859,7 +794,7 @@ int MeadowlarkLC::OnRetardance(MM::PropertyBase* pProp, MM::ActionType eAct, lon retardanceT = ceilf(retardanceT * 10000) / 10000; double voltage = round(RetardanceToVoltage(retardanceT, index)); - if (controllerType_ == g_ControllerDeviceType10V) { + if (controllerType_ == g_ControllerDeviceType10V_D5020) { if (voltage >= 0 && voltage <= 10000) { voltLimitCheck = true; } @@ -882,7 +817,7 @@ int MeadowlarkLC::OnRetardance(MM::PropertyBase* pProp, MM::ActionType eAct, lon if (voltage < 0) { voltage = 0; } - else if (controllerType_ == g_ControllerDeviceType10V) { + else if (controllerType_ == g_ControllerDeviceType10V_D5020) { if (voltage > 10000) { voltage = 10000; } @@ -939,7 +874,7 @@ int MeadowlarkLC::OnVoltage(MM::PropertyBase* pProp, MM::ActionType eAct, long i double voltage = GetVoltage(index); // in mV double maxV = 10000; - if (controllerType_ == g_ControllerDeviceType20V_D3060HV || controllerType_ == g_ControllerDeviceType20V_D5020) { + if (controllerType_ == g_ControllerDeviceType20V_D5020) { maxV = 20000; } @@ -962,7 +897,7 @@ int MeadowlarkLC::OnVoltage(MM::PropertyBase* pProp, MM::ActionType eAct, long i voltage *= 1000; // now in mV double maxV = 10000; - if (controllerType_ == g_ControllerDeviceType20V_D3060HV || controllerType_ == g_ControllerDeviceType20V_D5020) { + if (controllerType_ == g_ControllerDeviceType20V_D5020) { maxV = 20000; } @@ -2346,46 +2281,11 @@ bool MeadowlarkLC::checkConfigFile(std::string configFilename) { void MeadowlarkLC::controllerLcTypeChange() { // Add multiple curves switch and load from resource ID // - if (controllerLCType_ == g_ControllerLCType_B001) { - controllerLCType_Curve = g_ControllerLCType_B001; - loadResource(IDR_TEXT1); - convertStringtoStringArray(lcCurve_); - } - else if (controllerLCType_ == g_ControllerLCType_B002) { - controllerLCType_Curve = g_ControllerLCType_B002; - loadResource(IDR_TEXT2); - convertStringtoStringArray(lcCurve_); - } - else if (controllerLCType_ == g_ControllerLCType_B14181) { - controllerLCType_Curve = g_ControllerLCType_B14181_Curves; - loadResource(IDR_B14181); - convertStringtoStringArray(lcCurve_); - } - else if (controllerLCType_ == g_ControllerLCType_B14182) { - controllerLCType_Curve = g_ControllerLCType_B14182_Curves; - loadResource(IDR_B14182); - convertStringtoStringArray(lcCurve_); - } - else if (controllerLCType_ == g_ControllerLCType_B14183) { - controllerLCType_Curve = g_ControllerLCType_B14183_Curves; - loadResource(IDR_B14183); - convertStringtoStringArray(lcCurve_); - } - else if (controllerLCType_ == g_ControllerLCType_T001) { - controllerLCType_Curve = g_ControllerLCType_T001_Curves; - loadResource(IDR_T001); - convertStringtoStringArray(lcCurve_); - } - else if (controllerLCType_ == g_ControllerLCType_F001 || controllerLCType_ == g_ControllerLCType_F001b) { + if (controllerLCType_ == g_ControllerLCType_F001) { controllerLCType_Curve = g_ControllerLCType_F001_Curves; loadDefault(); import(controllerLCType_Curve); } - else if (controllerLCType_ == g_ControllerLCType_F002) { - controllerLCType_Curve = serialnum_ + g_ControllerLCType_F002_Curves; - loadDefault(); - import(controllerLCType_Curve); - } else if (controllerLCType_ == g_ControllerLCType_Internal) { loadDefault(); } From fdbd28621a498c0fe0867855f5db8ee0a7ce22ee Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Tue, 4 Apr 2023 11:22:52 -0700 Subject: [PATCH 25/29] clean up header --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h | 6 ------ 1 file changed, 6 deletions(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h index be7e0bda1..312f0b0db 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h @@ -56,7 +56,6 @@ class MeadowlarkLC : public CGenericBase void GetName(char* pszName) const; bool Busy(); - int GetVLCSerialAnswer(const char* portName, const char* term, std::string& ans); // int Initialize(MM::Device& device, MM::Core& core); @@ -68,10 +67,6 @@ class MeadowlarkLC : public CGenericBase // action interface // --------------- - int OnPort(MM::PropertyBase* pProp, MM::ActionType eAct); - int OnBaud(MM::PropertyBase* pProp, MM::ActionType eAct); - int OnBriefMode(MM::PropertyBase* pProp, MM::ActionType eAct); - int OnSerialNumber(MM::PropertyBase* pProp, MM::ActionType eAct); int OnDevAdapterVersionNumber(MM::PropertyBase* pProp, MM::ActionType eAct); int OnActivationKey(MM::PropertyBase* pProp, MM::ActionType eAct); @@ -169,7 +164,6 @@ class MeadowlarkLC : public CGenericBase double VoltageToRetardance(double volt, long index); double RetardanceToVoltage(double retardance, long index); - double RetardanceToVoltage(long wIndex, double AbsRetardance); double GetVoltage(long index); void SendVoltageToDevice(int volt16bit, long index); From a12a6975806899dde6f594bf8d6e136b1c3838ef Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Tue, 4 Apr 2023 11:56:13 -0700 Subject: [PATCH 26/29] enable internal curve at init --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp | 7 +------ 1 file changed, 1 insertion(+), 6 deletions(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp index 6bf8ed835..dedc3f0ad 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp @@ -247,7 +247,7 @@ MeadowlarkLC::MeadowlarkLC() : pAct = new CPropertyAction(this, &MeadowlarkLC::OnControllerLCType); CreateProperty("Select LC Type", g_ControllerLCType_F001, MM::String, false, pAct, true); AddAllowedValue("Select LC Type", g_ControllerLCType_F001); - //AddAllowedValue("Select LC Type", g_ControllerLCType_Internal); + AddAllowedValue("Select LC Type", g_ControllerLCType_Internal); pAct = new CPropertyAction(this, &MeadowlarkLC::OnSerialNumber); @@ -292,11 +292,6 @@ int MeadowlarkLC::Initialize() return ERR_INVALID_SERIAL_NUMBER; } - // Why do we raise an error here? - if (controllerLCType_ == g_ControllerLCType_Internal) { - return ERR_INVALID_LC_SELECTION; - } - if (controllerLCType_ == "Undefined" || controllerLCType_ == "") { return ERR_INVALID_LCSERIAL_NUMBER; } From fb24f3ecf9d00fbc942411e8693412389a3d86b0 Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Tue, 4 Apr 2023 12:25:57 -0700 Subject: [PATCH 27/29] move out internal calibration curve --- .../MeadowlarkLC/InternalCalibrationCurve.h | 230 ++++++++++++++++++ DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp | 1 + DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h | 205 ---------------- .../MeadowlarkLC/MeadowlarkLC.vcxproj | 2 + 4 files changed, 233 insertions(+), 205 deletions(-) create mode 100644 DeviceAdapters/MeadowlarkLC/InternalCalibrationCurve.h diff --git a/DeviceAdapters/MeadowlarkLC/InternalCalibrationCurve.h b/DeviceAdapters/MeadowlarkLC/InternalCalibrationCurve.h new file mode 100644 index 000000000..176591f76 --- /dev/null +++ b/DeviceAdapters/MeadowlarkLC/InternalCalibrationCurve.h @@ -0,0 +1,230 @@ +/////////////////////////////////////////////////////////////////////////////// +// FILE: InternalCalibrationCurve.h +// PROJECT: Micro-Manager +// SUBSYSTEM: DeviceAdapters +//----------------------------------------------------------------------------- +// DESCRIPTION: Voltage (mV) versus retardance (nm) internal LC calibration +// curve acquired at 546 nm. Used when no LC-specific calibration +// curve is provided. +// +// AUTHOR: Amitabh Verma +// Ivan Ivanov +// +// COPYRIGHT: Marine Biological Laboratory (2011 - 2017) +// Chan Zuckerberg Biohub San Francisco (2017 - 2023) +// +// 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. + +#pragma once + +extern const int ArrayLengthDefault = 198; +// LC Calibration curve Voltage(mV) vs Absolute Retardance(nm) +extern const double ArrayDefaultLcVoltagesRet[ArrayLengthDefault][3] = { + {0,1284.343,1284.343}, + {200,1284.411,1284.411}, + {400,1284.0869,1284.0869}, + {600,1283.8796,1283.8796}, + {800,1283.3625,1283.3625}, + {800.0002,1283.2228,1283.2228}, + {800.0005,1283.3013,1283.3013}, + {800.0013,1283.415,1283.415}, + {800.0025,1283.3468,1283.3468}, + {800.0045,1283.4783,1283.4783}, + {800.0074,1283.3376,1283.3376}, + {800.0117,1283.3345,1283.3345}, + {800.0179,1283.4308,1283.4308}, + {800.0264,1283.496,1283.496}, + {800.0377,1283.4891,1283.4891}, + {800.0527,1283.4348,1283.4348}, + {800.0721,1283.7001,1283.7001}, + {800.0969,1283.6556,1283.6556}, + {800.128,1283.7085,1283.7085}, + {800.1666,1283.7365,1283.7365}, + {800.214,1283.7697,1283.7697}, + {800.2716,1283.6506,1283.6506}, + {800.3411,1283.7167,1283.7167}, + {800.424,1283.6982,1283.6982}, + {800.5223,1283.7743,1283.7743}, + {800.638,1283.8627,1283.8627}, + {800.7734,1283.7518,1283.7518}, + {800.9308,1283.8488,1283.8488}, + {801.113,1283.8833,1283.8833}, + {801.3225,1283.8304,1283.8304}, + {801.5625,1283.8893,1283.8893}, + {801.8361,1283.8992,1283.8992}, + {802.1468,1283.9257,1283.9257}, + {802.4982,1283.9562,1283.9562}, + {802.8941,1284.0687,1284.0687}, + {803.3387,1284.1172,1284.1172}, + {803.8364,1284.0798,1284.0798}, + {804.3917,1284.0042,1284.0042}, + {805.0095,1284.047,1284.047}, + {805.6949,1284.0695,1284.0695}, + {806.4534,1284.1594,1284.1594}, + {807.2906,1284.1851,1284.1851}, + {808.2125,1284.1339,1284.1339}, + {809.2255,1284.2399,1284.2399}, + {810.336,1284.2579,1284.2579}, + {811.5509,1284.3578,1284.3578}, + {812.8775,1284.1702,1284.1702}, + {814.3233,1284.2469,1284.2469}, + {815.8961,1284.1438,1284.1438}, + {817.6041,1284.283,1284.283}, + {819.4559,1284.301,1284.301}, + {821.4603,1284.2782,1284.2782}, + {823.6266,1284.1348,1284.1348}, + {825.9644,1284.2441,1284.2441}, + {828.4838,1284.1818,1284.1818}, + {831.1949,1284.3066,1284.3066}, + {834.1088,1284.2123,1284.2123}, + {837.2363,1284.1847,1284.1847}, + {840.5892,1284.2885,1284.2885}, + {844.1794,1284.2258,1284.2258}, + {848.0192,1284.1924,1284.1924}, + {852.1216,1284.3458,1284.3458}, + {856.4996,1284.1655,1284.1655}, + {861.1669,1284.0703,1284.0703}, + {866.1377,1284.145,1284.145}, + {871.4266,1284.1002,1284.1002}, + {877.0485,1284.0598,1284.0598}, + {883.0189,1284.0197,1284.0197}, + {889.3539,1283.9844,1283.9844}, + {896.0698,1283.9204,1283.9204}, + {903.1836,1283.9547,1283.9547}, + {910.7126,1283.9744,1283.9744}, + {918.675,1283.9253,1283.9253}, + {927.0889,1283.9131,1283.9131}, + {935.9734,1283.7408,1283.7408}, + {945.3481,1283.6477,1283.6477}, + {955.2328,1283.6884,1283.6884}, + {965.6481,1283.6045,1283.6045}, + {976.6151,1283.4708,1283.4708}, + {988.1553,1283.4731,1283.4731}, + {1000.2911,1283.4991,1283.4991}, + {1013.0452,1283.2888,1283.2888}, + {1026.4408,1283.2068,1283.2068}, + {1040.502,1282.854,1282.854}, + {1055.2531,1282.8246,1282.8246}, + {1070.7194,1282.4509,1282.4509}, + {1086.9263,1282.1366,1282.1366}, + {1103.9004,1281.6805,1281.6805}, + {1121.6683,1281.3497,1281.3497}, + {1140.2579,1280.9851,1280.9851}, + {1159.6971,1280.6768,1280.6768}, + {1180.0148,1280.2689,1280.2689}, + {1201.2404,1279.3618,1279.3618}, + {1223.4039,1278.7089,1278.7089}, + {1246.5363,1277.9419,1277.9419}, + {1270.6688,1276.0315,1276.0315}, + {1295.8336,1274.8234,1274.8234}, + {1322.0635,1272.7963,1272.7963}, + {1349.3917,1270.1302,1270.1302}, + {1377.8527,1266.1652,1266.1652}, + {1407.4811,1260.8419,1260.8419}, + {1438.3125,1253.3003,1253.3003}, + {1470.3833,1244.5061,1244.5061}, + {1503.7303,1232.5726,1232.5726}, + {1538.3914,1217.3304,1217.3304}, + {1574.4049,1198.2084,1198.2084}, + {1611.8101,1176.7759,1176.7759}, + {1650.6469,1154.4043,1154.4043}, + {1690.9559,1128.3533,1128.3533}, + {1732.7789,1089,1089}, + {1821.1359,1047.5177,1047.5177}, + {1867.7567,1016.2104,1016.2104}, + {1916.0651,984.7769,984.7769}, + {1966.1063,953.2874,953.2874}, + {2017.9265,920.6101,920.6101}, + {2071.573,887.09,887.09}, + {2127.0933,851.7007,851.7007}, + {2184.5361,816.75,816.75}, + {2305.3887,754.0078,754.0078}, + {2368.8997,721.3992,721.3992}, + {2434.5366,689.3527,689.3527}, + {2502.3521,658.8939,658.8939}, + {2572.3999,628.5602,628.5602}, + {2644.7349,599.2983,599.2983}, + {2719.4126,569.1844,569.1844}, + {2796.4893,544.5,544.5}, + {2958.0703,491.2751,491.2751}, + {3042.6919,468.1365,468.1365}, + {3129.9478,446.146,446.146}, + {3219.8982,425.1326,425.1326}, + {3312.6057,405.4332,405.4332}, + {3408.1331,387.0562,387.0562}, + {3506.5439,369.5298,369.5298}, + {3607.9033,353.7877,353.7877}, + {3712.2771,338.264,338.264}, + {3819.7314,324.5506,324.5506}, + {3930.3347,308.7356,308.7356}, + {4044.1553,296.194,296.194}, + {4161.2627,284.466,284.466}, + {4281.728,272.25,272.25}, + {4533.0195,249.2416,249.2416}, + {4663.9917,240.8623,240.8623}, + {4798.6152,231.4884,231.4884}, + {4936.9644,221.9211,221.9211}, + {5079.1172,214.1089,214.1089}, + {5225.1514,206.1059,206.1059}, + {5375.145,199.4312,199.4312}, + {5529.1787,192.4627,192.4627}, + {5687.3335,186.2214,186.2214}, + {5849.6919,179.7628,179.7628}, + {6016.3364,173.8859,173.8859}, + {6187.3521,168.3429,168.3429}, + {6362.8232,162.9014,162.9014}, + {6542.8379,157.5549,157.5549}, + {6727.4824,152.6496,152.6496}, + {6916.8462,147.6369,147.6369}, + {7111.019,143.0052,143.0052}, + {7310.0918,138.6415,138.6415}, + {7514.1567,134.3855,134.3855}, + {7723.3071,130.3516,130.3516}, + {7937.6372,126.2824,126.2824}, + {8157.2432,122.406,122.406}, + {8382.2217,118.8456,118.8456}, + {8612.6699,115.4299,115.4299}, + {8848.6885,111.6104,111.6104}, + {9090.377,108.5394,108.5394}, + {9337.8359,105.2933,105.2933}, + {9591.1699,102.3992,102.3992}, + {9850.4814,99.3358,99.3358}, + {10115.876,96.4839,96.4839}, + {10387.4609,93.7825,93.7825}, + {10665.3428,91.202,91.202}, + {10949.6318,88.5837,88.5837}, + {11240.4365,86.0813,86.0813}, + {11537.8691,83.6826,83.6826}, + {11842.042,81.2935,81.2935}, + {12153.0684,79.0205,79.0205}, + {12471.0654,76.9506,76.9506}, + {12796.1484,75.0336,75.0336}, + {13128.4346,72.9454,72.9454}, + {13468.0439,70.8509,70.8509}, + {13815.0967,69.1639,69.1639}, + {14169.7139,67.2585,67.2585}, + {14532.0195,65.5513,65.5513}, + {14902.1367,63.9257,63.9257}, + {15280.1924,61.706,61.706}, + {15666.3135,60.4764,60.4764}, + {16060.627,58.9538,58.9538}, + {16463.2637,57.8524,57.8524}, + {16874.3535,55.6492,55.6492}, + {17294.0312,54.4416,54.4416}, + {17722.4277,53.0858,53.0858}, + {18159.6816,51.6723,51.6723}, + {18605.9258,50.635,50.635}, + {19061.3008,49.3032,49.3032}, + {19525.9453,47.6384,47.6384}, + {20000,46.83,46.83} + +}; \ No newline at end of file diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp index dedc3f0ad..2e8e32b83 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp @@ -43,6 +43,7 @@ #include "MeadowlarkLC.h" #include "usbdrvd.h" #include "resource.h" +#include "InternalCalibrationCurve.h" //////// Micro-manager interface ////////// #include "ModuleInterface.h" diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h index 312f0b0db..ce2461663 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.h @@ -189,209 +189,4 @@ class MeadowlarkLC : public CGenericBase bool checkConfigFile(std::string strings); }; - -const int ArrayLengthDefault = 198; -// LC Calibration curve Voltage(mV) vs Absolute Retardance(nm) -const double ArrayDefaultLcVoltagesRet[ArrayLengthDefault][3] = { - {0,1284.343,1284.343}, - {200,1284.411,1284.411}, - {400,1284.0869,1284.0869}, - {600,1283.8796,1283.8796}, - {800,1283.3625,1283.3625}, - {800.0002,1283.2228,1283.2228}, - {800.0005,1283.3013,1283.3013}, - {800.0013,1283.415,1283.415}, - {800.0025,1283.3468,1283.3468}, - {800.0045,1283.4783,1283.4783}, - {800.0074,1283.3376,1283.3376}, - {800.0117,1283.3345,1283.3345}, - {800.0179,1283.4308,1283.4308}, - {800.0264,1283.496,1283.496}, - {800.0377,1283.4891,1283.4891}, - {800.0527,1283.4348,1283.4348}, - {800.0721,1283.7001,1283.7001}, - {800.0969,1283.6556,1283.6556}, - {800.128,1283.7085,1283.7085}, - {800.1666,1283.7365,1283.7365}, - {800.214,1283.7697,1283.7697}, - {800.2716,1283.6506,1283.6506}, - {800.3411,1283.7167,1283.7167}, - {800.424,1283.6982,1283.6982}, - {800.5223,1283.7743,1283.7743}, - {800.638,1283.8627,1283.8627}, - {800.7734,1283.7518,1283.7518}, - {800.9308,1283.8488,1283.8488}, - {801.113,1283.8833,1283.8833}, - {801.3225,1283.8304,1283.8304}, - {801.5625,1283.8893,1283.8893}, - {801.8361,1283.8992,1283.8992}, - {802.1468,1283.9257,1283.9257}, - {802.4982,1283.9562,1283.9562}, - {802.8941,1284.0687,1284.0687}, - {803.3387,1284.1172,1284.1172}, - {803.8364,1284.0798,1284.0798}, - {804.3917,1284.0042,1284.0042}, - {805.0095,1284.047,1284.047}, - {805.6949,1284.0695,1284.0695}, - {806.4534,1284.1594,1284.1594}, - {807.2906,1284.1851,1284.1851}, - {808.2125,1284.1339,1284.1339}, - {809.2255,1284.2399,1284.2399}, - {810.336,1284.2579,1284.2579}, - {811.5509,1284.3578,1284.3578}, - {812.8775,1284.1702,1284.1702}, - {814.3233,1284.2469,1284.2469}, - {815.8961,1284.1438,1284.1438}, - {817.6041,1284.283,1284.283}, - {819.4559,1284.301,1284.301}, - {821.4603,1284.2782,1284.2782}, - {823.6266,1284.1348,1284.1348}, - {825.9644,1284.2441,1284.2441}, - {828.4838,1284.1818,1284.1818}, - {831.1949,1284.3066,1284.3066}, - {834.1088,1284.2123,1284.2123}, - {837.2363,1284.1847,1284.1847}, - {840.5892,1284.2885,1284.2885}, - {844.1794,1284.2258,1284.2258}, - {848.0192,1284.1924,1284.1924}, - {852.1216,1284.3458,1284.3458}, - {856.4996,1284.1655,1284.1655}, - {861.1669,1284.0703,1284.0703}, - {866.1377,1284.145,1284.145}, - {871.4266,1284.1002,1284.1002}, - {877.0485,1284.0598,1284.0598}, - {883.0189,1284.0197,1284.0197}, - {889.3539,1283.9844,1283.9844}, - {896.0698,1283.9204,1283.9204}, - {903.1836,1283.9547,1283.9547}, - {910.7126,1283.9744,1283.9744}, - {918.675,1283.9253,1283.9253}, - {927.0889,1283.9131,1283.9131}, - {935.9734,1283.7408,1283.7408}, - {945.3481,1283.6477,1283.6477}, - {955.2328,1283.6884,1283.6884}, - {965.6481,1283.6045,1283.6045}, - {976.6151,1283.4708,1283.4708}, - {988.1553,1283.4731,1283.4731}, - {1000.2911,1283.4991,1283.4991}, - {1013.0452,1283.2888,1283.2888}, - {1026.4408,1283.2068,1283.2068}, - {1040.502,1282.854,1282.854}, - {1055.2531,1282.8246,1282.8246}, - {1070.7194,1282.4509,1282.4509}, - {1086.9263,1282.1366,1282.1366}, - {1103.9004,1281.6805,1281.6805}, - {1121.6683,1281.3497,1281.3497}, - {1140.2579,1280.9851,1280.9851}, - {1159.6971,1280.6768,1280.6768}, - {1180.0148,1280.2689,1280.2689}, - {1201.2404,1279.3618,1279.3618}, - {1223.4039,1278.7089,1278.7089}, - {1246.5363,1277.9419,1277.9419}, - {1270.6688,1276.0315,1276.0315}, - {1295.8336,1274.8234,1274.8234}, - {1322.0635,1272.7963,1272.7963}, - {1349.3917,1270.1302,1270.1302}, - {1377.8527,1266.1652,1266.1652}, - {1407.4811,1260.8419,1260.8419}, - {1438.3125,1253.3003,1253.3003}, - {1470.3833,1244.5061,1244.5061}, - {1503.7303,1232.5726,1232.5726}, - {1538.3914,1217.3304,1217.3304}, - {1574.4049,1198.2084,1198.2084}, - {1611.8101,1176.7759,1176.7759}, - {1650.6469,1154.4043,1154.4043}, - {1690.9559,1128.3533,1128.3533}, - {1732.7789,1089,1089}, - {1821.1359,1047.5177,1047.5177}, - {1867.7567,1016.2104,1016.2104}, - {1916.0651,984.7769,984.7769}, - {1966.1063,953.2874,953.2874}, - {2017.9265,920.6101,920.6101}, - {2071.573,887.09,887.09}, - {2127.0933,851.7007,851.7007}, - {2184.5361,816.75,816.75}, - {2305.3887,754.0078,754.0078}, - {2368.8997,721.3992,721.3992}, - {2434.5366,689.3527,689.3527}, - {2502.3521,658.8939,658.8939}, - {2572.3999,628.5602,628.5602}, - {2644.7349,599.2983,599.2983}, - {2719.4126,569.1844,569.1844}, - {2796.4893,544.5,544.5}, - {2958.0703,491.2751,491.2751}, - {3042.6919,468.1365,468.1365}, - {3129.9478,446.146,446.146}, - {3219.8982,425.1326,425.1326}, - {3312.6057,405.4332,405.4332}, - {3408.1331,387.0562,387.0562}, - {3506.5439,369.5298,369.5298}, - {3607.9033,353.7877,353.7877}, - {3712.2771,338.264,338.264}, - {3819.7314,324.5506,324.5506}, - {3930.3347,308.7356,308.7356}, - {4044.1553,296.194,296.194}, - {4161.2627,284.466,284.466}, - {4281.728,272.25,272.25}, - {4533.0195,249.2416,249.2416}, - {4663.9917,240.8623,240.8623}, - {4798.6152,231.4884,231.4884}, - {4936.9644,221.9211,221.9211}, - {5079.1172,214.1089,214.1089}, - {5225.1514,206.1059,206.1059}, - {5375.145,199.4312,199.4312}, - {5529.1787,192.4627,192.4627}, - {5687.3335,186.2214,186.2214}, - {5849.6919,179.7628,179.7628}, - {6016.3364,173.8859,173.8859}, - {6187.3521,168.3429,168.3429}, - {6362.8232,162.9014,162.9014}, - {6542.8379,157.5549,157.5549}, - {6727.4824,152.6496,152.6496}, - {6916.8462,147.6369,147.6369}, - {7111.019,143.0052,143.0052}, - {7310.0918,138.6415,138.6415}, - {7514.1567,134.3855,134.3855}, - {7723.3071,130.3516,130.3516}, - {7937.6372,126.2824,126.2824}, - {8157.2432,122.406,122.406}, - {8382.2217,118.8456,118.8456}, - {8612.6699,115.4299,115.4299}, - {8848.6885,111.6104,111.6104}, - {9090.377,108.5394,108.5394}, - {9337.8359,105.2933,105.2933}, - {9591.1699,102.3992,102.3992}, - {9850.4814,99.3358,99.3358}, - {10115.876,96.4839,96.4839}, - {10387.4609,93.7825,93.7825}, - {10665.3428,91.202,91.202}, - {10949.6318,88.5837,88.5837}, - {11240.4365,86.0813,86.0813}, - {11537.8691,83.6826,83.6826}, - {11842.042,81.2935,81.2935}, - {12153.0684,79.0205,79.0205}, - {12471.0654,76.9506,76.9506}, - {12796.1484,75.0336,75.0336}, - {13128.4346,72.9454,72.9454}, - {13468.0439,70.8509,70.8509}, - {13815.0967,69.1639,69.1639}, - {14169.7139,67.2585,67.2585}, - {14532.0195,65.5513,65.5513}, - {14902.1367,63.9257,63.9257}, - {15280.1924,61.706,61.706}, - {15666.3135,60.4764,60.4764}, - {16060.627,58.9538,58.9538}, - {16463.2637,57.8524,57.8524}, - {16874.3535,55.6492,55.6492}, - {17294.0312,54.4416,54.4416}, - {17722.4277,53.0858,53.0858}, - {18159.6816,51.6723,51.6723}, - {18605.9258,50.635,50.635}, - {19061.3008,49.3032,49.3032}, - {19525.9453,47.6384,47.6384}, - {20000,46.83,46.83} - -}; - - #endif //_MEADOWLARKLC_H_ diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj index ed01c6d4a..f8ac1f3fc 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.vcxproj @@ -11,7 +11,9 @@ + + From b3585427397e13797e56d64ca8fea6240b27f52e Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Fri, 14 Apr 2023 15:16:55 -0700 Subject: [PATCH 28/29] remove old win32 code --- DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp | 4 ---- 1 file changed, 4 deletions(-) diff --git a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp index 2e8e32b83..1cc560ded 100644 --- a/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp +++ b/DeviceAdapters/MeadowlarkLC/MeadowlarkLC.cpp @@ -23,10 +23,6 @@ // INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES. -#ifdef WIN32 -// #include -#define snprintf _snprintf -#endif #include #include From 0fdb6ae6180a1ed6e4990af52bfa4381cee54fca Mon Sep 17 00:00:00 2001 From: Ivan Ivanov Date: Fri, 14 Apr 2023 15:36:00 -0700 Subject: [PATCH 29/29] Distribute mmgr_dal_MeadowlarkLC.csv with MM build --- DeviceAdapters/MeadowlarkLC/build.xml | 7 + .../MeadowlarkLC/mmgr_dal_MeadowlarkLC.csv | 202 ++++++++++++++++++ 2 files changed, 209 insertions(+) create mode 100644 DeviceAdapters/MeadowlarkLC/build.xml create mode 100644 DeviceAdapters/MeadowlarkLC/mmgr_dal_MeadowlarkLC.csv diff --git a/DeviceAdapters/MeadowlarkLC/build.xml b/DeviceAdapters/MeadowlarkLC/build.xml new file mode 100644 index 000000000..9ab88008c --- /dev/null +++ b/DeviceAdapters/MeadowlarkLC/build.xml @@ -0,0 +1,7 @@ + + + + + + + diff --git a/DeviceAdapters/MeadowlarkLC/mmgr_dal_MeadowlarkLC.csv b/DeviceAdapters/MeadowlarkLC/mmgr_dal_MeadowlarkLC.csv new file mode 100644 index 000000000..fe75fb838 --- /dev/null +++ b/DeviceAdapters/MeadowlarkLC/mmgr_dal_MeadowlarkLC.csv @@ -0,0 +1,202 @@ +Voltage(mv),490-A,490-B,Voltage(mv),546-A,546-B,Voltage(mv),630-A,630-B +-,-,-,-,-,-,-,-,- +0,490,490,0,546,546,0,630,630 +0,970.6205,924.4288,0,932.2446,891.2008,0,899.6626,857.2885 +200,970.7488,924.4422,200,932.2028,891.1546,200,899.5908,857.3078 +400,970.1024,924.3969,400,932.1573,891.1184,400,899.5674,857.255 +600,970.3032,924.2089,600,932.0445,890.9534,600,899.4894,857.1558 +800,970.6216,924.0334,800,931.9086,890.7409,800,899.2996,857.0418 +800.0002,970.2955,923.9782,800.0002,931.8625,890.7854,800.0002,899.3223,857.0668 +800.0005,970.5338,924.0236,800.0005,931.8528,890.7086,800.0005,899.3418,857.0194 +800.0013,970.4291,923.9744,800.0013,931.8522,890.7479,800.0013,899.5204,857.0292 +800.0025,970.2023,923.9342,800.0025,931.8227,890.7476,800.0025,899.462,857.0341 +800.0045,970.303,924.0377,800.0045,931.7548,890.6813,800.0045,899.5118,857.0626 +800.0074,970.7298,923.9681,800.0074,931.7547,890.6643,800.0074,899.361,857.0405 +800.0117,970.501,923.949,800.0117,931.6918,890.6855,800.0117,899.4615,857.0678 +800.0179,970.6304,923.9568,800.0179,931.6571,890.686,800.0179,899.4302,857.0682 +800.0264,970.3965,924.0368,800.0264,931.6416,890.6548,800.0264,899.625,857.0418 +800.0377,970.1071,923.9077,800.0377,931.6307,890.6253,800.0377,899.5439,857.0936 +800.0527,970.485,923.9475,800.0527,931.5721,890.6281,800.0527,899.5349,857.0681 +800.0721,970.2087,923.9111,800.0721,931.5644,890.6214,800.0721,899.5664,857.0282 +800.0969,970.3183,923.9297,800.0969,931.5154,890.5881,800.0969,899.6073,857.0379 +800.128,970.7083,923.9536,800.128,931.5333,890.5963,800.128,899.5505,857.0487 +800.1666,970.2427,923.9435,800.1666,931.46,890.51,800.1666,899.6141,857.0633 +800.214,970.4091,923.8931,800.214,931.4731,890.5632,800.214,899.6068,857.0994 +800.2716,970.3083,923.8519,800.2716,931.4268,890.519,800.2716,899.5877,857.0792 +800.3411,970.5234,923.9288,800.3411,931.3978,890.5178,800.3411,899.5906,857.0653 +800.424,970.6236,923.8934,800.424,931.3268,890.5305,800.424,899.6685,857.0522 +800.5223,970.3292,923.9189,800.5223,931.3256,890.5302,800.5223,899.5839,857.0637 +800.638,970.2563,923.9035,800.638,931.314,890.4742,800.638,899.6397,856.998 +800.7734,970.5975,923.856,800.7734,931.2654,890.4747,800.7734,899.6262,857.0522 +800.9308,970.3166,923.8568,800.9308,931.2437,890.4885,800.9308,899.7133,857.012 +801.113,970.3415,923.8309,801.113,931.2462,890.4669,801.113,899.6783,857.0919 +801.3225,970.2266,923.8604,801.3225,931.2007,890.4383,801.3225,899.715,857.1085 +801.5625,970.1211,923.8718,801.5625,931.1546,890.4131,801.5625,899.7017,857.0707 +801.8361,970.3842,923.8087,801.8361,931.1307,890.4269,801.8361,899.6898,857.0624 +802.1468,970.3016,923.8685,802.1468,931.1105,890.4143,802.1468,899.7621,857.0792 +802.4982,969.985,923.791,802.4982,931.137,890.3937,802.4982,899.827,857.0773 +802.8941,970.217,923.8154,802.8941,931.0918,890.3479,802.8941,899.6497,857.0718 +803.3387,970.3767,923.7698,803.3387,931.0677,890.4115,803.3387,899.6829,857.0474 +803.8364,970.3445,923.7722,803.8364,931.037,890.3945,803.8364,899.6318,857.1147 +804.3917,970.5901,923.8733,804.3917,931.0189,890.4064,804.3917,899.7525,857.0555 +805.0095,970.566,923.7935,805.0095,930.9893,890.4003,805.0095,899.6837,857.0744 +805.6949,970.0751,923.7876,805.6949,930.9831,890.3537,805.6949,899.8142,857.1001 +806.4534,970.1019,923.7536,806.4534,930.9687,890.3165,806.4534,899.7499,857.0536 +807.2906,970.332,923.7192,807.2906,930.897,890.351,807.2906,899.6883,857.0696 +808.2125,970.0452,923.8179,808.2125,930.9462,890.3187,808.2125,899.7281,857.0939 +809.2255,970.4099,923.7689,809.2255,930.9235,890.2614,809.2255,899.7595,857.0351 +810.336,970.2049,923.7425,810.336,930.87,890.3649,810.336,899.8073,857.0397 +811.5509,970.522,923.7787,811.5509,930.8652,890.2741,811.5509,899.7525,857.064 +812.8775,970.5826,923.695,812.8775,930.8035,890.3727,812.8775,899.8117,857.0436 +814.3233,970.468,923.7678,814.3233,930.822,890.3077,814.3233,899.6554,857.0988 +815.8961,970.1391,923.8174,815.8961,930.812,890.3015,815.8961,899.8895,857.0988 +817.6041,969.946,923.7242,817.6041,930.7932,890.3216,817.6041,899.7247,857.0803 +819.4559,970.2611,923.6915,819.4559,930.7858,890.2636,819.4559,899.686,857.0612 +821.4603,970.3737,923.7487,821.4603,930.7503,890.2589,821.4603,899.723,857.0939 +823.6266,970.5807,923.7081,823.6266,930.7581,890.2311,823.6266,899.7955,857.1255 +825.9644,970.033,923.7018,825.9644,930.7242,890.2486,825.9644,899.812,857.0459 +828.4838,970.3193,923.6777,828.4838,930.701,890.2911,828.4838,899.7655,857.0563 +831.1949,970.292,923.7104,831.1949,930.6909,890.2283,831.1949,899.7504,857.0718 +834.1088,970.2877,923.6915,834.1088,930.7001,890.2129,834.1088,899.8679,857.0621 +837.2363,970.686,923.6729,837.2363,930.683,890.211,837.2363,899.8172,857.0741 +840.5892,970.2121,923.6927,840.5892,930.6551,890.2355,840.5892,899.6591,857.0527 +844.1794,970.1685,923.6724,844.1794,930.6496,890.191,844.1794,899.7956,857.0781 +848.0192,970.2287,923.6824,848.0192,930.6663,890.2072,848.0192,899.8628,857.054 +852.1216,970.068,923.5919,852.1216,930.638,890.1694,852.1216,899.7232,857.0361 +856.4996,970.3734,923.6727,856.4996,930.6429,890.178,856.4996,899.8561,857.0196 +861.1669,970.3137,923.598,861.1669,930.6287,890.1575,861.1669,899.9128,857.0443 +866.1377,970.1763,923.6608,866.1377,930.6719,890.1467,866.1377,899.7827,857.0599 +871.4266,969.8468,923.6149,871.4266,930.6586,890.1859,871.4266,899.8221,857.0342 +877.0485,970.2015,923.613,877.0485,930.6082,890.1552,877.0485,899.7712,857.0002 +883.0189,970.1778,923.579,883.0189,930.5925,890.0991,883.0189,899.7446,857.0287 +889.3539,970.1403,923.5471,889.3539,930.5999,890.0855,889.3539,899.821,857.0339 +896.0698,970.1182,923.6089,896.0698,930.6033,890.181,896.0698,899.7709,857.0079 +903.1836,970.3028,923.5931,903.1836,930.5726,890.1472,903.1836,899.746,857.0137 +910.7126,970.4548,923.5502,910.7126,930.5873,890.1114,910.7126,899.7554,857.0063 +918.675,970.282,923.4852,918.675,930.6237,890.1854,918.675,899.7675,856.9862 +927.0889,970.4199,923.4875,927.0889,930.5857,890.1284,927.0889,899.7549,856.9512 +935.9734,970.1215,923.4682,935.9734,930.6266,890.1038,935.9734,899.7319,856.9774 +945.3481,970.2079,923.4111,945.3481,930.5223,890.0535,945.3481,899.6938,856.9719 +955.2328,970.3379,923.4767,955.2328,930.5933,890.0286,955.2328,899.653,856.9655 +965.6481,970.2631,923.4019,965.6481,930.5941,890.0884,965.6481,899.7375,856.9472 +976.6151,970.3875,923.4012,976.6151,930.5687,890.0451,976.6151,899.6376,856.9833 +988.1553,970.2522,923.4086,988.1553,930.5385,890.0163,988.1553,899.7427,856.9252 +1000.2911,969.9078,923.3596,1000.2911,930.557,890.0491,1000.2911,899.6805,856.8859 +1013.0452,970.0635,923.3773,1013.0452,930.5176,890.0396,1013.0452,899.6723,856.8544 +1026.4408,970.2175,923.3554,1026.4408,930.5435,890.0295,1026.4408,899.7247,856.8285 +1040.502,970.128,923.2605,1040.502,930.5205,889.9334,1040.502,899.6249,856.8191 +1055.2531,970.2524,923.2151,1055.2531,930.5279,889.9079,1055.2531,899.564,856.7766 +1070.7194,970.1076,923.2344,1070.7194,930.489,889.9186,1070.7194,899.5818,856.6044 +1086.9263,970.1007,923.2286,1086.9263,930.4697,889.8162,1086.9263,899.4997,856.5801 +1103.9004,969.9478,923.0824,1103.9004,930.4439,889.8192,1103.9004,899.5999,856.5523 +1121.6683,970.1496,923.0922,1121.6683,930.4274,889.778,1121.6683,899.5002,856.4835 +1140.2579,970.1148,923.0065,1140.2579,930.4343,889.7391,1140.2579,899.4736,856.4471 +1159.6971,969.9048,922.923,1159.6971,930.3959,889.6096,1159.6971,899.4955,856.3932 +1180.0148,970.3169,922.9155,1180.0148,930.3518,889.6253,1180.0148,899.5243,856.417 +1201.2404,970.1703,922.937,1201.2404,930.3223,889.5322,1201.2404,899.4092,856.3383 +1223.4039,970.0681,922.7351,1223.4039,930.3196,889.4193,1223.4039,899.3651,856.2585 +1246.5363,969.613,922.6464,1246.5363,930.3167,889.3759,1246.5363,899.2998,856.1673 +1270.6688,969.828,922.5366,1270.6688,930.2458,889.2964,1270.6688,899.2124,855.9028 +1295.8336,969.1636,922.373,1295.8336,930.0862,889.1425,1295.8336,899.1862,855.7897 +1322.0635,969.7645,922.1286,1322.0635,930.012,888.9792,1322.0635,898.9433,855.6584 +1349.3917,969.4572,921.9927,1349.3917,929.8615,888.7347,1349.3917,898.849,855.5537 +1377.8527,969.3201,921.727,1377.8527,929.7949,888.5834,1377.8527,898.6525,855.3041 +1407.4811,968.6626,921.4118,1407.4811,929.611,888.2929,1407.4811,898.5597,854.9843 +1438.3125,968.3328,921.0574,1438.3125,929.3736,887.8838,1438.3125,898.2804,854.603 +1470.3833,967.3712,920.6402,1470.3833,929.0931,887.5446,1470.3833,898.0769,854.241 +1503.7303,966.8077,920.0765,1503.7303,928.7357,886.9879,1503.7303,897.7363,853.6616 +1538.3914,966.1992,919.3054,1538.3914,928.278,886.2698,1538.3914,897.1968,852.9628 +1574.4049,965.9624,918.276,1574.4049,927.5916,885.3224,1574.4049,896.7646,852.1288 +1611.8101,965.0162,916.9243,1611.8101,926.6802,884.0146,1611.8101,895.7163,850.8418 +1650.6469,963.3153,915.1328,1650.6469,925.5521,882.2684,1650.6469,894.6274,849.2033 +1690.9559,961.3159,912.6903,1690.9559,923.8433,879.9159,1690.9559,893.1882,846.8071 +1732.7789,957.9959,908.7847,1732.7789,921.199,876.0469,1732.7789,890.7143,843.2004 +1776.1578,953.3476,903.0673,1776.1578,917.0734,870.5281,1776.1578,886.8367,837.9049 +1821.1359,946.827,895.4383,1821.1359,911.2153,863.1636,1821.1359,881.443,830.8559 +1867.7567,936.6005,884.2268,1867.7567,901.9248,852.217,1867.7567,872.9053,820.4144 +1916.0651,921.1646,868.6462,1916.0651,887.6832,816,1916.0651,859.9327,806.0139 +1966.1063,903.3099,851.4998,1966.1063,870.5569,803.2164,1966.1063,844.155,790.2736 +2017.9265,882.2637,831.6913,2017.9265,849.5167,780.3251,2017.9265,825.0329,771.9366 +2071.573,857.5798,808.7895,2071.573,816,758.4372,2071.573,802.6772,750.7388 +2127.0933,833.5766,786.0417,2184.5361,783.7935,734.9517,2127.0933,780.4465,729.9273 +2184.5361,807.8544,761.1958,2243.9512,756.5076,710.5395,2184.5361,756.6233,707.4849 +2243.9512,780.4788,735,2305.3887,731.0079,686.5345,2243.9512,731.5385,683.7009 +2305.3887,735,686.3516,2368.8997,704.4125,661.3734,2305.3887,706.9906,660.626 +2434.5366,700.7076,659.4877,2434.5366,677.1952,635.7903,2368.8997,681.0876,630 +2502.3521,672.9132,633.7493,2502.3521,650.9499,610.9731,2434.5366,633,588.9432 +2572.3999,644.8488,607.1382,2572.3999,624.2265,585.107,2572.3999,605.1533,564.1947 +2644.7349,617.1823,580.9291,2644.7349,597.4565,544,2644.7349,579.3066,539.9846 +2719.4126,590.1406,555.2892,2719.4126,570.524,512.6885,2719.4126,554.5247,516.4898 +2796.4893,563.6783,529.9413,2796.4893,544,488.5669,2796.4893,530.1088,493.3978 +2876.0225,537.1005,490,2958.0703,496.5517,465.6986,2876.0225,506.0818,470.6246 +2958.0703,511.063,460.3628,3042.6919,472.0698,443.351,2958.0703,483.0397,448.8235 +3042.6919,490,437.8198,3129.9478,449.3098,422.3942,3042.6919,460.5412,427.463 +3219.8982,441.8552,416.4667,3219.8982,427.2246,402.0498,3219.8982,417.7865,387.7795 +3312.6057,420.1671,396.3131,3312.6057,406.6101,382.7645,3312.6057,397.7541,369.1588 +3408.1331,399.9636,377.3401,3408.1331,387.1375,364.4818,3408.1331,378.7257,351.6688 +3506.5439,380.6215,359.1884,3506.5439,368.5356,347.1151,3506.5439,360.4048,335.6093 +3607.9033,362.6565,342.2755,3607.9033,351.1603,330.7877,3607.9033,343.2813,315 +3712.2771,345.6025,326.2427,3712.2771,334.5208,315.3003,3712.2771,316.5,288.067 +3819.7314,329.4085,311.116,3819.7314,318.8302,300.9774,3930.3347,297.8997,275.4721 +3930.3347,314.5246,296.9482,3930.3347,303.6891,288.1786,4044.1553,284.4137,263.1691 +4044.1553,300.2228,283.4467,4044.1553,289.3447,272,4161.2627,271.9346,251.5433 +4161.2627,286.9457,271.1392,4161.2627,272,248.9747,4281.728,260.048,240.7095 +4281.728,274.1207,259.4746,4405.6226,255.0143,238.8121,4405.6226,248.7716,230.5889 +4405.6226,262.7582,245,4533.0195,243.8904,229.0572,4533.0195,240.9365,220.9525 +4533.0195,245,228.2811,4663.9917,233.6463,219.631,4663.9917,231.459,212.1722 +4798.6152,232.2119,218.7595,4798.6152,224.2706,210.9779,4798.6152,219.9905,203.5433 +4936.9644,223.0139,210.2967,4936.9644,215.3646,202.6757,4936.9644,211.4631,195.6999 +5079.1172,214.1941,202.4314,5079.1172,207.0312,194.9609,5079.1172,203.5765,188.2723 +5225.1514,205.8129,194.719,5225.1514,199.0388,187.6683,5225.1514,195.8127,181.215 +5375.145,198.1253,187.4335,5375.145,191.7614,180.7153,5375.145,188.8701,174.5527 +5529.1787,190.8561,180.6313,5529.1787,184.7471,174.3025,5529.1787,182.1455,168.2452 +5687.3335,184.0166,174.2024,5687.3335,178.1785,168.0974,5687.3335,175.8348,162.2989 +5849.6919,177.3959,168.0324,5849.6919,171.8573,162.1696,5849.6919,170.2077,156.6466 +6016.3364,171.3813,162.1559,6016.3364,165.8826,156.6108,6016.3364,164.3174,151.2501 +6187.3521,165.3328,156.6941,6187.3521,160.2345,151.2442,6187.3521,158.8593,146.1486 +6362.8232,159.8003,151.4475,6362.8232,154.7769,146.1721,6362.8232,153.4872,141.2436 +6542.8379,154.4813,146.4201,6542.8379,149.5208,141.2655,6542.8379,148.7406,136.5876 +6727.4824,149.315,141.4647,6727.4824,144.6192,136.694,6727.4824,143.3614,132.0617 +6916.8462,144.3994,136.9317,6916.8462,139.8528,132.2138,6916.8462,138.611,127.813 +7111.019,139.6884,132.4532,7111.019,135.3087,127.9781,7111.019,134.1671,123.6539 +7310.0918,135.1608,128.2527,7310.0918,130.8717,123.8625,7310.0918,129.6289,119.7295 +7514.1567,130.8677,124.2037,7514.1567,126.6624,119.9076,7514.1567,125.3573,115.9217 +7723.3071,126.7117,120.2176,7723.3071,122.6289,116.1569,7723.3071,121.244,112.2621 +7937.6372,122.7271,116.4833,7937.6372,118.7922,112.5721,7937.6372,117.392,108.8654 +8157.2432,118.8601,112.874,8157.2432,114.9512,109.0352,8157.2432,113.632,105.4071 +8382.2217,115.0413,109.3423,8382.2217,111.3614,105.6748,8382.2217,110.0651,102.113 +8612.6699,111.5769,105.9814,8612.6699,107.8823,102.4275,8612.6699,106.4587,99.0125 +8848.6885,108.1115,102.7166,8848.6885,104.4973,99.2904,8848.6885,103.0587,96.0089 +9090.377,104.7823,99.6065,9090.377,101.3092,96.3812,9090.377,99.7892,93.1148 +9337.8359,101.5812,96.5673,9337.8359,98.2542,93.5584,9337.8359,96.736,90.3426 +9591.1699,98.4565,93.7296,9591.1699,95.2408,90.7208,9591.1699,93.6189,87.643 +9850.4814,95.4768,90.8826,9850.4814,92.3161,87.9936,9850.4814,90.7617,85.0927 +10115.876,92.5906,88.1795,10115.876,89.4552,85.3829,10115.876,87.9421,82.5253 +10387.4609,89.7896,85.5828,10387.4609,86.8021,82.8705,10387.4609,85.1449,80.0759 +10665.3428,87.1324,83.1083,10665.3428,84.1937,80.4809,10665.3428,82.5527,77.7494 +10949.6318,84.5107,80.6835,10949.6318,81.6002,78.0902,10949.6318,79.9311,75.4634 +11240.4365,81.9955,78.3251,11240.4365,79.1326,75.8564,11240.4365,77.3833,73.3033 +11537.8691,79.5643,76.0659,11537.8691,76.7868,73.6304,11537.8691,75.1805,71.2253 +11842.042,77.1485,73.9059,11842.042,74.4716,71.4253,11842.042,72.6283,69.0601 +12153.0684,74.8872,71.8079,12153.0684,72.2637,69.5549,12153.0684,70.368,67.1042 +12471.0654,72.6868,69.6891,12471.0654,70.0873,67.5314,12471.0654,68.1573,65.323 +12796.1484,70.5127,67.7043,12796.1484,67.9739,65.5203,12796.1484,65.8804,63.4326 +13128.4346,68.3415,65.7709,13128.4346,65.9837,63.6358,13128.4346,63.7574,61.602 +13468.0439,66.3098,63.9008,13468.0439,63.8888,61.8589,13468.0439,61.7415,59.8026 +13815.0967,64.4313,62.0415,13815.0967,62.0409,60.1542,13815.0967,59.6705,58.071 +14169.7139,62.5952,60.3645,14169.7139,60.1749,58.4695,14169.7139,57.7055,56.5971 +14532.0195,60.7655,58.6476,14532.0195,58.2799,56.8153,14532.0195,55.7588,54.9204 +14902.1367,59.0105,57.0212,14902.1367,56.4299,55.1376,14902.1367,53.9353,53.3453 +15280.1924,57.145,55.441,15280.1924,54.8112,53.7054,15280.1924,52.2118,51.7954 +15666.3135,55.3077,53.7107,15666.3135,53.0993,52.1366,15666.3135,50.3359,50.394 +16060.627,53.8139,52.2771,16060.627,51.5603,50.6507,16060.627,48.7272,49.1797 +16463.2637,52.1141,50.7996,16463.2637,50.0864,49.4051,16463.2637,47.2134,47.784 +16874.3535,50.6181,49.4089,16874.3535,48.4409,48.03,16874.3535,45.6533,46.4252 +17294.0312,49.0191,47.8965,17294.0312,46.7223,46.6243,17294.0312,44.0655,45.1176 +17722.4277,47.7337,46.6729,17722.4277,45.3696,45.3731,17722.4277,42.4901,43.8982 +18159.6816,46.1009,45.4193,18159.6816,43.8406,44.0624,18159.6816,41.2069,42.7917 +18605.9258,44.6626,44.0637,18605.9258,42.549,42.7944,18605.9258,39.7559,41.6228 +19061.3008,43.3413,42.872,19061.3008,41.1453,41.7694,19061.3008,38.4585,40.4752 +19525.9453,41.9732,41.6098,19525.9453,39.9507,40.701,19525.9453,37.063,39.1899 +20000,40.5954,40.4874,20000,38.6905,39.5402,20000,35.5043,38.1445 +-,-,-,-,-,-,-,-,-