/*
 * zGo2System.h
 *
 * Gocator system communication library
 * Copyright (C) 2010 by LMI Technologies Inc.
 *
 * Licensed under The MIT License.
 * Redistributions of files must retain the above copyright notice.
 */
#ifndef LMITECH_GO2_Z_SYSTEM_H_INCLUDED
#define LMITECH_GO2_Z_SYSTEM_H_INCLUDED

#include <Go2System.h>
#include <z/zGo2Object.h>
#include <z/zGo2Part.h>
#include <z/zGo2Profile.h>
#include <z/zGo2Range.h>
#include <z/zGo2Output.h>
#include <z/zGo2Sensor.h>
#include <z/zzFireSync.h>
#include <zXml.h>
#include <zReceiver.h>
#include <zThread.h>
#include <Go2ApiBegin.h>

/*
 * Go2SystemInfo Class
 */

typedef zHandle Go2SystemInfo;

typedef struct Go2SystemInfoClass
{
    GO2_OBJECT_FIELDS();

    Go2User currentUser;
    Go2SystemState systemState;
    Go2CalibrationState calibrationState;

    Go2SensorInfo* hostDevice;
    Go2SensorInfo* assignedDevice;
    zList visibleDevices;
} Go2SystemInfoClass;

GO2_EXPORT(Go2Status) Go2SystemInfo_Construct(Go2SystemInfo* info);
GO2_EXPORT(Go2Status) Go2SystemInfo_Init(Go2SystemInfo info);
GO2_EXPORT(Go2Status) Go2SystemInfo_VRelease(Go2SystemInfo info);

GO2_EXPORT(Go2Status) Go2SystemInfo_Read(Go2SystemInfo* info, zSerializer reader);

GO2_EXPORT(Go2User) Go2SystemInfo_CurrentUser(Go2SystemInfo info);
GO2_EXPORT(Go2SystemState) Go2SystemInfo_SystemState(Go2SystemInfo info);
GO2_EXPORT(Go2CalibrationState) Go2SystemInfo_CalibrationState(Go2SystemInfo info);

GO2_EXPORT(const Go2SensorInfo*) Go2SystemInfo_AssignedDevice(Go2SystemInfo info);

GO2_EXPORT(Go2UInt32) Go2SystemInfo_VisibleDeviceCount(Go2SystemInfo info);
GO2_EXPORT(const Go2SensorInfo*) Go2SystemInfo_VisibleDeviceAt(Go2SystemInfo info, Go2UInt32 index);
GO2_EXPORT(const Go2SensorInfo*) Go2SystemInfo_FindVisibleDevice(Go2SystemInfo info, Go2UInt32 id);

GO2_EXPORT(const Go2SensorInfo*) Go2SystemInfo_HostDevice(Go2SystemInfo info);

/*
 * Go2System Class
 */

#define GO2_SYSTEM_CLIENT_PROTOCOL_MAJOR                          (8)
#define GO2_SYSTEM_CLIENT_PROTOCOL_MINOR                          (0)

#define GO2_SYSTEM_CONFIG_SCHEMA_VERSION                          (8)

#define GO2_SYSTEM_TRANSFORM_SCHEMA_VERSION                       (4)

#define GO2_SYSTEM_DATA_PORT                                      (3196)

#define GO2_SYSTEM_UPGRADE_STATUS_PERIOD                          (1000000)

#define GO2_SYSTEM_CONTROL_GET_VERSION                            (0x4511)
#define GO2_SYSTEM_CONTROL_GET_VERSION_TIMEOUT                    (1000000)

#define GO2_SYSTEM_CONTROL_LOG_IN                                 (0x4003)
#define GO2_SYSTEM_CONTROL_LOG_IN_TIMEOUT                         (500000)

#define GO2_SYSTEM_CONTROL_CHANGE_PASSWORD                        (0x4004)
#define GO2_SYSTEM_CONTROL_CHANGE_PASSWORD_TIMEOUT                (3000000)

#define GO2_SYSTEM_CONTROL_CHANGE_BUDDIES                         (0x4005)
#define GO2_SYSTEM_CONTROL_CHANGE_BUDDIES_TIMEOUT                 (10000000)

#define GO2_SYSTEM_CONTROL_GET_SYSTEM_INFO                        (0x4002)
#define GO2_SYSTEM_CONTROL_GET_SYSTEM_INFO_TIMEOUT                (2000000)

#define GO2_SYSTEM_CONTROL_GET_DEFAULT_FILE                       (0x4100)
#define GO2_SYSTEM_CONTROL_GET_DEFAULT_FILE_TIMEOUT               (1000000)

#define GO2_SYSTEM_CONTROL_SET_DEFAULT_FILE                       (0x4101)
#define GO2_SYSTEM_CONTROL_SET_DEFAULT_FILE_TIMEOUT               (5000000)

#define GO2_SYSTEM_CONTROL_GET_LOADED_FILE                        (0x4512)
#define GO2_SYSTEM_CONTROL_GET_LOADED_FILE_TIMEOUT                (1000000)

#define GO2_SYSTEM_CONTROL_SET_CONNECTION_TYPE                    (0x4514)
#define GO2_SYSTEM_CONTROL_SET_CONNECTION_TYPE_TIMEOUT            (5000000)

#define GO2_SYSTEM_CONTROL_GET_CONNECTION_TYPE                    (0x4515)
#define GO2_SYSTEM_CONTROL_GET_CONNECTION_TYPE_TIMEOUT            (1000000)

#define GO2_SYSTEM_CONTROL_TRIGGER                                (0x4510)
#define GO2_SYSTEM_CONTROL_TRIGGER_TIMEOUT                        (1000000)

#define GO2_SYSTEM_CONTROL_RESET                                  (0x4300)
#define GO2_SYSTEM_CONTROL_RESET_TIMEOUT                          (3000000)

#define GO2_SYSTEM_CONTROL_RESTORE_FACTORY                        (0x4301)
#define GO2_SYSTEM_CONTROL_RESTORE_FACTORY_TIMEOUT                (15000000)

#define GO2_SYSTEM_CONTROL_CLEAR_CALIBRATION                      (0x4102)
#define GO2_SYSTEM_CONTROL_CLEAR_CALIBRATION_TIMEOUT              (5000000)

#define GO2_SYSTEM_CONTROL_GET_REFERENCE_IMAGE_STATE              (0x451A)
#define GO2_SYSTEM_CONTROL_GET_REFERENCE_IMAGE_STATE_TIMEOUT      (5000000)

#define GO2_SYSTEM_CONTROL_CLEAR_REFERENCE_IMAGE                  (0x451B)
#define GO2_SYSTEM_CONTROL_CLEAR_REFERENCE_IMAGE_TIMEOUT          (5000000)

#define GO2_SYSTEM_CONTROL_CLEAR_PROFILE_TEMPLATE                 (0x4103)
#define GO2_SYSTEM_CONTROL_CLEAR_PROFILE_TEMPLATE_TIMEOUT         (5000000)

#define GO2_SYSTEM_CONTROL_CLEAR_MEASUREMENT_STATS                (0x4526)

#define GO2_SYSTEM_CONTROL_GET_STATES                             (0x4525)

//TODO: Remove this command from the API as it should be implemented in zFireSync
#define GO2_SYSTEM_CONTROL_GET_ENCODER                            (0x101C)
#define GO2_SYSTEM_CONTROL_GET_ENCODER_TIMEOUT                    (1000000)

//TODO: Remove this command from the API as it should be implemented in zFireSync
#define GO2_SYSTEM_CONTROL_SCHEDULE_START                         (0x101D)
#define GO2_SYSTEM_CONTROL_SCHEDULE_START_TIMEOUT                 (10000000)

#define GO2_SYSTEM_CONTROL_SCHEDULE_DIGITAL_OUTPUT                (0x4518)
#define GO2_SYSTEM_CONTROL_SCHEDULE_DIGITAL_OUTPUT_TIMEOUT        (1000000)

#define GO2_SYSTEM_CONTROL_SCHEDULE_ANALOG_OUTPUT                 (0x4519)
#define GO2_SYSTEM_CONTROL_SCHEDULE_ANALOG_OUTPUT_TIMEOUT         (1000000)

#define GO2_SYSTEM_TRANSFORM_NAME                                 "_live.tfm"

#define GO2_SYSTEM_RECONNECT_HOLD_DURATION                        (40000000)

typedef struct Go2SystemClass
{
    GO2_OBJECT_FIELDS();

    zIPAddress serverAddress;
    zFireSync fireSync;
    Go2Version remoteProtocol;

    zReceiver dataReceiver;
    Go2HealthCallback dataCallback;
    zHandle dataContext;

    zReceiver healthReceiver;
    Go2HealthCallback healthCallback;
    zHandle healthContext;

    Go2Range rangeModule;
    Go2Profile profileModule;
    Go2Output outputModule;
    Go2Output partModule;
    zList sensors;

    zBool isLoaded;
    zBool isModified;
    zBool isTransformModified;
    Go2Changes changes;

    Go2User user;
    Go2SystemState systemState;
    Go2CalibrationState calibrationState;
    Go2Bool temperatureSafetyEnabled;
    Go2Bool temperatureSafetyValid;
    Go2SystemState startupState;
    Go2Mode startupMode;
    zList startupModeOptions;

    Go2SpotDetectionType spotDetectionType;
    Go2Double spotDetectionThreshold;
    Go2Double spotDetectionMaxWidth;
    Go2SpotSelectionType spotSelectionType;

    Go2TriggerSource triggerSource;
    Go2SystemDomain systemDomain;
    Go2UInt32 triggerDelay;
    Go2UInt32 triggerDelayMin;
    Go2UInt32 triggerDelayMax;
    Go2Bool triggerGateEnabled;

    Go2Bool fullFrameRateEnabled;

    Go2Bool occlusionReductionEnabled;

    Go2Double frameRateMin;
    Go2Double frameRateMax;
    Go2Double frameRate;
    Go2FrameRateMaxSource frameRateMaxSource;

    Go2Double encoderPeriodMin;
    Go2Double encoderPeriodMax;
    Go2Double encoderPeriod;
    Go2EncoderPeriodMinSource encoderPeriodMinSource;
    Go2EncoderTriggerMode encoderTriggerMode;

    Go2Bool buddyReversed;
    Go2Orientation orientation;
    Go2Bool overlapEnabled;
    Go2Bool intensityEnabled;
    Go2UInt32 batchCount;
    Go2UInt32 batchCountMin;
    Go2UInt32 batchCountMax;

    Go2CalibrationSource calibrationSource;
    Go2Double travelSpeed;
    Go2Double travelResolution;
    Go2CalibrationTarget alignmentTarget;
    Go2CalibrationTarget travelTarget;
    Go2Double diskDiameter;
    Go2Double diskHeight;
    Go2Double barWidth;
    Go2Double barHeight;
    Go2UInt32 barHoleCount;
    Go2Double barHoleDistance;
    Go2Double barHoleDiameter;
    Go2Double plateHeight;
    Go2UInt32 plateHoleCount;
    Go2Double plateRefHoleDiameter;
    Go2Double plateSecHoleDiameter;

    Go2Double calibratedX;
    Go2Double calibratedY;
    Go2Double calibratedZ;
    Go2Double calibratedWidth;
    Go2Double calibratedLength;
    Go2Double calibratedHeight;
    
    zBool xSmoothingEnabled; 
    z64f xSmoothingWindow; 
    z64f xSmoothingWindowMax; 
    z64f xSmoothingWindowMin; 

    zBool ySmoothingEnabled; 
    z64f ySmoothingWindow; 
    z64f ySmoothingWindowMax; 
    z64f ySmoothingWindowMin; 

    zBool xGapFillingEnabled; 
    z64f xGapFillingWindow; 
    z64f xGapFillingWindowMax; 
    z64f xGapFillingWindowMin; 

    zBool yGapFillingEnabled; 
    z64f yGapFillingWindow; 
    z64f yGapFillingWindowMax; 
    z64f yGapFillingWindowMin; 

    Go2ResamplingType xResamplingType;
    z64f xResamplingInterval;
    
    zXml custom;
    zBool autoSyncEnabled;
} Go2SystemClass;

GO2_EXPORT(Go2Status) Go2System_Init(Go2System system);
GO2_EXPORT(Go2Status) Go2System_VRelease(Go2System system);

GO2_EXPORT(Go2Status) Go2System_TryLoad(Go2System system);
GO2_EXPORT(Go2Status) Go2System_Load(Go2System system);
GO2_EXPORT(Go2Status) Go2System_Unload(Go2System system);

GO2_EXPORT(Go2Status) Go2System_OnHealth(Go2System system, zReceiver receiver, zResult result);
GO2_EXPORT(Go2Status) Go2System_OnData(Go2System system, zReceiver receiver, zResult result);

GO2_EXPORT(Go2Status) Go2System_ReadConfig(Go2System system, zBool isLoading);
GO2_EXPORT(Go2Status) Go2System_WriteConfig(Go2System system);
GO2_EXPORT(Go2Status) Go2System_SyncConfig(Go2System system);
GO2_EXPORT(Go2Status) Go2System_SetLiveConfig(Go2System system, zXml config);
GO2_EXPORT(Go2Status) Go2System_FlushChanges(Go2System system);
GO2_EXPORT(Go2Status) Go2System_GetLiveConfig(Go2System system, zXml* config);
GO2_EXPORT(Go2Status) Go2System_SetModified(Go2System system);

GO2_EXPORT(Go2Status) Go2System_ReadInfo(Go2System system, zBool isLoading);
GO2_EXPORT(Go2Status) Go2System_SyncInfo(Go2System system);
GO2_EXPORT(Go2Status) Go2System_GetInfo(Go2System system, Go2SystemInfo* sytemInfo);

GO2_EXPORT(Go2Status) Go2System_ReadTransform(Go2System system, zBool isLoading);
GO2_EXPORT(Go2Status) Go2System_WriteTransform(Go2System system);
GO2_EXPORT(Go2Status) Go2System_SyncTransform(Go2System system);
GO2_EXPORT(Go2Status) Go2System_GetTransform(Go2System system, zXml* transform);
GO2_EXPORT(Go2Status) Go2System_SetTransform(Go2System system, zXml transform);
GO2_EXPORT(Go2Status) Go2System_FlushTransformChanges(Go2System system);
GO2_EXPORT(Go2Status) Go2System_SetTransformModified(Go2System system);

GO2_EXPORT(Go2Status) Go2System_Ping(Go2System system);

GO2_EXPORT(Go2Status) Go2System_ChangeRole(Go2System system, Go2Sensor sensor, Go2SensorRole role);
GO2_EXPORT(Go2Status) Go2System_ChangeRoles(Go2System system, Go2SensorRole role, const z32u* buddyIds, z32u count);

GO2_EXPORT(Go2Status) Go2System_Set32u(Go2System system, Go2UInt32* field, Go2UInt32 input, Go2UInt32 min, Go2UInt32 max);
GO2_EXPORT(Go2Status) Go2System_Set32s(Go2System system, Go2Int32* field, Go2Int32 input, Go2Int32 min, Go2Int32 max);
GO2_EXPORT(Go2Status) Go2System_Set64f(Go2System system, Go2Double* field, Go2Double input, Go2Double min, Go2Double max);
GO2_EXPORT(Go2Status) Go2System_SetText(Go2System system, Go2Char* field, Go2UInt32 fieldCapacity, const Go2Char* input);
GO2_EXPORT(Go2Status) Go2System_SetOption(Go2System system, Go2UInt32* field, Go2UInt32 value, const Go2UInt32* options, Go2UInt32 optionCount);
GO2_EXPORT(Go2Status) Go2System_AddOption(Go2System system, zList valueList, Go2UInt32 value, const Go2UInt32* options, Go2UInt32 optionCount);
GO2_EXPORT(Go2Status) Go2System_RemoveOption(Go2System system, zList valueList, Go2UInt32 index);
GO2_EXPORT(Go2Status) Go2System_ClearOptions(Go2System system, zList valueList);

GO2_EXPORT(Go2Status) Go2System_CheckConfigurable(Go2System system);
GO2_EXPORT(Go2Status) Go2System_CheckConnected(Go2System system);
GO2_EXPORT(Go2Status) Go2System_CheckState(Go2System system, Go2SystemState requiredState);

GO2_EXPORT(Go2Status) Go2System_GetVersion(Go2System system, Go2Version* version);

GO2_EXPORT(Go2Status) Go2System_EnableAutoSync(Go2System system, Go2Bool enable);
GO2_EXPORT(Go2Bool) Go2System_AutoSyncEnabled(Go2System system);


#include <Go2ApiEnd.h>

#endif          /* #ifndef LMITECH_GO2_Z_SYSTEM_H_INCLUDED */
