<< Click to Display Table of Contents >> Navigation: NmxDLL Referenz > HowTo > Reading static data > Event based |
Reading event based first requires registering a notification. In the following example, message based notifications are used.
A good practice is:
Every-time the notification NMXNOTIFY_NEW_STATIC32 occurs (= a message is received), a flag is set. In a separate timer routine, this flag is checked. If set, static data is readout via NMX_StaticGet32_1.
If event based data read-out is used, then a connection breakdown is typically handled using the notification NMXNOTIFY_FAILURE_DATA_EXCHANGE. Therefore no special error handling is done in the following sample code.
C / C++
// Define Message. In VisualStudio, WM_USER is defined in WinUser.h as:
// #define WM_USER 0x0400
#define WM_MESSAGE_NEW_STATIC32 (WM_USER + NMXNOTIFY_NEW_STATIC32)
// Global declaration
BOOL bNewStatic = false;
// Global definition
#define N_STATIC_CH_DISPLAY (64) // Max number of static channels used. Adapt it to your needs.
#define N_DIGIIO_DISPLAY (128) // Max number of digital inputs used. Adapt it to your needs.
#define N_MAX_BOXES (32) // Max number of boxes supported.
// ###-> Register notification, e.g. directly after connecting.
if (NMX_RegisterMessage_1(pHandle, NMXNOTIFY_NEW_STATIC32, static_cast<HWND>(Handle.ToPointer()), WM_MESSAGE_NEW_STATIC32, 0, 0) != NST_SUCCESS) {
// Handle error
}
// ###-> Implement message handler
protected: virtual void WndProc(Message% m) override
{
/* Listen for operating system messages. */
switch (m.Msg)
{
case WM_MESSAGE_NEW_STATIC32:
bNewStatic = true;
break;
default:
/* Pass all standard messages to the GUI form. */
Form::WndProc(m);
break;
}
}
// ###-> Implement timer and timer-event-handler, Interval e.g. 30ms
private: System::Void tmrStatic_Tick(System::Object^ sender, System::EventArgs^ e) {
// Disable this timer
tmrStatic->Enabled = false;
// Update static data, if new data available.
if (bNewStatic != false)
{
bNewStatic = false;
signed long aslMeasVal[N_STATIC_CH_DISPLAY];
unsigned char aucHardStat[N_STATIC_CH_DISPLAY];
unsigned char aucDigiIn[N_DIGIIO_DISPLAY / 8];
unsigned char aucBoxStatus[N_MAX_BOXES];
unsigned long ulNUpdates = 0;
memset(aslMeasVal, 0, sizeof(aslMeasVal));
memset(aucHardStat, 0, sizeof(aucHardStat));
memset(aucDigiIn, 0, sizeof(aucDigiIn));
memset(aucBoxStatus, 0, sizeof(aucBoxStatus));
if (NMX_StaticGet32_1(pHandleNmx, aslMeasVal, N_STATIC_CH_DISPLAY, aucHardStat, sizeof(aucHardStat), aucDigiIn, sizeof(aucDigiIn), aucBoxStatus, sizeof(aucBoxStatus), &ulNUpdates) == NST_SUCCESS)
{
// New data successfully received. Display, Calculate, Store, ...
}
}
// Re-enable this timer
tmrStatic->Enabled = true;
}
Delphi
// Define Message for "new static data available"
const WM_MESSAGE_NMX_NEWSTATIC = WM_USER + $10;
cMaxTotalChannels = 256; // Max number of static channels used. Adapt it to your needs.
cMaxDigiInBytes = 16; // Max number of digital input bytes used. Adapt it to your needs.
cMaxBoxes = 32; // Max number of boxes supported.
// Declaration of class variables.
bNewStaticData : Boolean;
// Declaration of message handler. Integrate it into the class declarations.
procedure OnMessageNewStatic32(var Msg: TMessage); message WM_MESSAGE_NMX_NEWSTATIC;
// ###-> Register notification, e.g. directly after connecting.
NMX_RegisterMessage_1(pNmxHandle, NMXNOTIFY_NEW_STATIC32, MainForm.Handle, WM_MESSAGE_NMX_NEWSTATIC, 0, 0);
// ###-> Implement message handler
procedure TMainForm.OnMessageNewStatic32(var Msg: TMessage);
begin
bNewStaticData := true;
end;
// ###-> Implement timer and timer-event-handler, Interval e.g. 30ms
procedure TMainForm.tmrUpdateStaticTimer(Sender: TObject);
var
aslValues : array [0..(cMaxTotalChannels-1)] of integer;
aucHardwareStatus : array [0..(cMaxTotalChannels-1)] of Byte;
aucDigiInBytes : array [0..(cMaxDigiInBytes-1)] of Byte;
aucBoxStatus : array [0..(cMaxBoxes-1)] of Byte;
ulUpdateCtr : Cardinal;
tStatus : NMX_STATUS;
begin
tmrUpdateStatic := false;
if bNewData then begin
bNewData := false;
tStatus := NMX_StaticGet32_1(pNmxHandle, @aslValues[0], cMaxTotalChannels,
@aucHardwareStatus[0], cMaxTotalChannels,
@aucDigiInBytes[0], cMaxDigiInBytes,
@aucBoxStatus[0], cMaxBoxes,
ulUpdateCtr);
if (tStatus = NST_SUCCESS) then begin
// New data successfully received. Display, Calculate, Store, ...
end;
end;
tmrUpdateStatic := true;
end;
C# / .Net
const int WM_MESSAGE_NEW_STATIC32 = WM_USER + 0x10; // Define Message for "new static data available"
const int N_STATIC_CH_DISPLAY = 64; // Max number of static channels used. Adapt it to your needs.
const int N_DIGIIO_DISPLAY = 128; // Max number of digital input bytes used. Adapt it to your needs.
const int N_BOXES_MAX = 32; // Max number of boxes supported.
// Global declaration
Boolean bNewStatic = false;
// ###-> Register notification, e.g. directly after connecting.
if (cNmx.RegisterMessage_1(pDevice, NMX_NOTIFICATION.NEW_STATIC32, Handle, WM_MESSAGE_NEW_STATIC32, 0, 0) != NMX_MSTATUS.SUCCESS)
{
// Handle error
}
// ###-> Implement message handler
protected override void WndProc(ref Message m)
{
// Listen for operating system messages.
switch (m.Msg)
{
case WM_MESSAGE_NEW_STATIC32:
bNewStatic = true;
break;
default:
/* Pass all standard messages to the GUI form. */
base.WndProc(ref m);
break;
}
}
// ###-> Implement timer and timer-event-handler, Interval e.g. 30ms
private void tmrStatic_Tick(object sender, EventArgs e)
{
/* Disable this timer */
tmrStatic.Enabled = false;
if (bNewStatic != false)
{
bNewStatic = false;
Int32[] aslMeasVal = new Int32[N_STATIC_CH_DISPLAY];
Byte[] aucHardStat = new Byte[N_STATIC_CH_DISPLAY];
Byte[] aucDigiIn = new Byte[N_DIGIIO_DISPLAY / 8];
Byte[] aucBoxStatus = new Byte[N_BOXES_MAX];
UInt32 ulNUpdates = 0;
if (cNmx.StaticGet32_1(pDevice, aslMeasVal, aucHardStat, aucDigiIn, aucBoxStatus, ref ulNUpdates) == NMX_MSTATUS.SUCCESS)
{
// New data successfully received. Display, Calculate, Store, ...
}
else
{
// Error reading data. Typical error: NST_DX_TIMEOUT_COMMON due to communication breakdown.
}
}
/* Re-enable this timer */
tmrStatic.Enabled = true;
}