LabVIEW

cancel
Showing results for 
Search instead for 
Did you mean: 

Call LabVIEW Virtual Instrument through ActiveX Server from C/C++

I am trying to access a VI by C/C++ almost identical to the reference example that can be found on this site for Visual Basic. However, somehow, I am unable to succeed to use the ActiveX Call() function. The program always crashes, whatever I try. Because the Visual Basic version works without any problems, I hope someone can point me the error in the code.

Thanks!




#include "stdafx.h"
#import "LabVIEW.tlb"

#define VIPATH "D:\\Program Files\\National Instruments\\LabVIEW 7.0\\examples\\apps\\freqresp.llb\\Frequency Response.vi"

using namespace LabVIEW;

int _tmain(int argc, _TCHAR* argv[])
{
// Initialization
HRESULT he = NULL;
he = CoInitialize(NULL);

// Create instance of
labview application engine
_ApplicationPtr pLV;
he = pLV.CreateInstance("LabVIEW.Application");

// Create instance of virtual instrument
VirtualInstrumentPtr pVI;
he = pVI.CreateInstance("LabVIEW.VirtualInstrument"); /* ?not? mandatory */

// Get reference to a VI at location VIPATH
_bstr_t viPath(VIPATH);
_bstr_t password("");
VARIANT_BOOL resvForCall = FALSE;
long options = 0;
pVI = pLV->GetVIReference(viPath,password,resvForCall,options);

// Show front panel
pVI->FPWinOpen = TRUE;

// Call the referenced VI as subVI
_variant_t paramNames[5] = {"Amplitude", "Number of Steps", "Low Frequency", "High Frequency", "Response Graph"};
_variant_t paramVals[5] = {}; /* VT_EMPTY */

/* Fill ParamVals with values from VI */
for (int i = 0; i < 5; ++i) paramVals[i] = pVI->GetControlValue(paramNames[i].bstrVal);

/* Call VI -> !!! CRASH !!! 😞 */
pVI->Call(paramNames,paramVals);

// Release references and close application
pLV->AutomaticC
lose = TRUE;
pVI.Release();
pLV.Release();
CoUninitialize();

return 0;
}
0 Kudos
Message 1 of 3
(3,393 Views)
This may not be the easiest way. Although i have not used _variant_t. But it seems like your VARIANT type is VT_EMPTY for everything. You need to build up an array of variants with correct type, that matches the type of control you are assigning data to like VT_INT for int numeric, VT_BSTR for string control etc

VARIANT paramNamesVarArg, paramValuesVarArg;
SAFEARRAY *paramNames, *paramValues;

::VariantInit(&paramNamesVarArg);
paramNamesVarArg.vt = VT_ARRAY | VT_BYREF | VT_BSTR;

// create safearray of strings
SAFEARRAYBOUND rgsabound[1];
rgsabound[0].lLbound = 0;
rgsabound[0].cElements = 1;
paramNames = SafeArrayCreate(VT_BSTR, 1, rgsabound);

paramNamesVarArg.pparray = &paramNames;

long index = 0;
_bstr_t paramName = "Numeric";
BSTR *bstrVal;
retVal = SafeArrayPtrOfIndex(paramNames, &index, (void **)&bstrVal);
*bstrVal = paramName.copy();

//do the same method for paramValuesVarArg
::VariantInit(&paramValuesVarArg);
paramValuesVarArg.vt = VT_ARRAY | VT_BYREF | VT_I4;

rgsabound[0].lLbound = 0;
rgsabound[0].cElements = 1;
paramValues = SafeArrayCreate(VT_VARIANT, 1, rgsabound);
paramValuesVarArg.pparray = &paramValues;

VARIANT *dispVarVal;
VARIANT tempVar;
tempVar.vt = VT_I4;
retVal = SafeArrayPtrOfIndex(paramValues, &index, (void **)&dispVarVal);
*dispVarVal = tempVar;

viPtr->Call(&paramNamesVarArg, &paramValuesVarArg);

Hope it helps.
A Rafiq
0 Kudos
Message 2 of 3
(3,373 Views)
Replace "¶mNames" with "&par amNames" (no spaces)
0 Kudos
Message 3 of 3
(3,371 Views)