banboshi_V1/halftoneproject-master/Code/Device/Axis.cs
2023-10-31 13:19:29 +08:00

816 lines
35 KiB
C#
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

using Advantech.Motion;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Security.Cryptography;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Timers;
namespace ProductionControl.Device
{
public class Axis : IDisposable
{
public enum AxisStateType
{
[Description("轴状态")]
AxisState = 0,
[Description("轴运动状态")]
AxisMotionState = 1,
[Description("轴IO状态")]
AxisIOState = 2,
}
public Action<int, AxisStateType, uint> axisStateEvent;
public enum AxisPosType
{
[Description("命令位置")]
CmdPos = 0,
[Description("反馈位置")]
ActualPos = 1,
}
public Action<int, AxisPosType, double> axisPosEvent;
/// <summary> 使用
/// 轴状态(AxisState 0-14) 单一值,无需按位取
/// STA_AxDisable -- 轴被禁用,用户可打开并激活
/// STA_AxReady ---- 轴已准备就绪,等待新的命令 *
/// STA_Stopping ---- 轴停止
/// STA_AxErrorStop --- 出现错误,轴停止
/// STA_AxHoming ---- 轴正在执行返回原点运动
/// STA_AxPtpMotion ---- 轴正在执行PTP 运动
/// STA_AxContiMotion ---- 轴正在执行连续运动
/// STA_AxSyncMotion --- 轴在一个群组中群组正在执行插补运动或轴是一个从轴正在执行Ecam/E-gear/Gantry 运动。
/// STA_AX_EXT_JOG -- 轴由外部信号控制。当外部信号激活时轴将执行JOG 模式运动。
/// STA_AX_EXT_MPG --- 轴由外部信号控制。当外部信号激活时轴将执行MPG 模式运动
/// </summary>
//public Action<int, int> axisStateEvent;
/// <summary>
/// 轴运动状态 使用
/// 位 说明
/// Stop ---- 停止
/// WaitERC---- 等待ERC 完成
/// InFA ---- 处于特定速度中 = FA
/// InFL ---- 处于低速中 = FL
/// InACC ---- 加速中
/// InFH ---- 处于最大速度中 = FH
/// InDEC ---- 减速中
/// WaitINP---- 到位等待
/// </summary>
//public Action<int, int> axisMotionStateEvent;
/// <summary>
/// 轴IO状态 (Ax_Motion_IO) 使用
/// RDY---- RDY 针脚输入
/// ALM ---- 报警信号输入 *
/// LMT+ ---- 限位开关+ *
/// LMT- ---- 限位开关- *
/// ORG---- 原始开关 *
/// DIR ---- DIR 输出
/// EMG ---- 紧急信号输入
/// INP ---- 到位信号输入
/// SVON ---- 伺服开启OUT6 *
/// ALRM ---- 报警复位输出状态
/// SLMT+ ---- 软件限位+
/// SLMT- ---- 软件限位-
/// CMP----- 比较信号OUT5
/// </summary>
//public Action<int, bool, bool, bool, bool> axisIOStateEvent;
/// <summary>
/// 告警(级别1 2 3)
/// </summary>
public Action<int, string> warningEvent;
/// <summary>
/// Log输出(0-info,1-warning 2-error)
/// </summary>
public Action<int, string> log;
/// <summary>
/// 设备列表多张PCI板卡
/// </summary>
public List<DEV_LIST> DevList { get; private set; }
/// <summary>
/// 设备数量
/// </summary>
//private uint deviceCount = 0;
/// <summary>
/// 设备号,用于打开设备(非索引)
/// </summary>
//public uint DeviceNum { get; private set; } = 0;
/// <summary>
/// 设备句柄
/// </summary>
private IntPtr m_DeviceHandle = IntPtr.Zero;
/// <summary>
/// 轴数量
/// </summary>
private uint m_ulAxisCount = 0;
private IntPtr[] m_Axishand = new IntPtr[0];
public double[] CmdPos { get; private set; } = new double[32];//轴命令位置
public double[] ActualPos { get; private set; } = new double[32];//轴实际(反馈)位置
public UInt16[] AxState { get; private set; } = new UInt16[32];//轴状态
public UInt32[] IOStatus { get; private set; } = new UInt32[32];//轴IO状态
public uint[] AxMotionState { get; private set; } = new uint[32];//轴运动状态
private uint[] AxEnableEvtArray = new uint[32];
private uint[] GpEnableEvt = new uint[32];
/// <summary>
/// 组
/// </summary>
private IntPtr m_GpHand = IntPtr.Zero;
/// <summary>
/// 是否打开设备成功
/// </summary>
public bool IsInit { get; private set; } = false;
Thread checkEventThread;
private System.Timers.Timer timer = new System.Timers.Timer();
/// <summary>
/// 获取设备列表
/// </summary>
/// <returns></returns>
/// <exception cref="Exception"></exception>
//public static List<DEV_LIST> getDevList()
//{
// DEV_LIST[] curAvailableDevs = new DEV_LIST[Motion.MAX_DEVICES];
// uint deviceCount = 0;
// int Result = Motion.mAcm_GetAvailableDevs(curAvailableDevs, Motion.MAX_DEVICES, ref deviceCount);
// if (Result != (int)ErrorCode.SUCCESS || curAvailableDevs.Length < 1)
// throw new Exception("Get Device Numbers Failed With Error Code: [0x" + Convert.ToString(Result, 16) + "] DevCount=" + curAvailableDevs.Length);
// return curAvailableDevs.ToList().Take((int)deviceCount).ToList();
//}
public Axis()
{
DEV_LIST[] curAvailableDevs = new DEV_LIST[Motion.MAX_DEVICES];
uint deviceCount = 0;
int Result = Motion.mAcm_GetAvailableDevs(curAvailableDevs, Motion.MAX_DEVICES, ref deviceCount);
if (Result != (int)ErrorCode.SUCCESS || curAvailableDevs.Length < 1)
throw new Exception("Get Device Numbers Failed With Error Code: [0x" + Convert.ToString(Result, 16) + "] DevCount=" + curAvailableDevs.Length);
DevList = curAvailableDevs.ToList().Take((int)deviceCount).ToList();
}
public void Dispose()
{
stop();
}
/// <summary>
/// 打开设备
/// </summary>
/// <exception cref="Exception"></exception>
public void start()
{
if (DevList == null || DevList.Count < 1)
throw new Exception("设备为空!");
start(DevList[0].DeviceNum);
}
public void start(uint DeviceNum)
{
if (IsInit) return;
//打开设备
uint uResult = Motion.mAcm_DevOpen(DeviceNum, ref m_DeviceHandle);
if (uResult != (int)ErrorCode.SUCCESS)
throw new Exception("Open Device Failed With Error Code: [0x" + Convert.ToString(uResult, 16) + "]");
//读取轴数量
uResult = Motion.mAcm_GetU32Property(m_DeviceHandle, (uint)PropertyID.FT_DevAxesCount, ref m_ulAxisCount);
if (uResult != (uint)ErrorCode.SUCCESS)
throw new Exception("Get Axis Number Failed With Error Code: [0x" + Convert.ToString(uResult, 16) + "]");
m_Axishand = new IntPtr[m_ulAxisCount];
//打开轴
for (int i = 0; i < m_ulAxisCount; i++)
{
//打开每个轴并获得每个轴句柄
uResult = Motion.mAcm_AxOpen(m_DeviceHandle, (UInt16)i, ref m_Axishand[i]);
if (uResult != (uint)ErrorCode.SUCCESS)
throw new Exception("Open Axis Failed With Error Code: [0x" + Convert.ToString(uResult, 16) + "]");
//打开电源使能,1: On
uResult = Motion.mAcm_AxSetSvOn(m_Axishand[i], 1);
if (uResult != (uint)ErrorCode.SUCCESS)
throw new Exception("Servo On Failed With Error Code: [0x" + Convert.ToString(uResult, 16) + "]");
//每个轴的初始属性(reset 命令位置和实际(反馈)位置)
//double cmdPosition = new double();
//cmdPosition = 0;
//为指定的轴设置命令位置
//Motion.mAcm_AxSetCmdPosition(m_Axishand[i], cmdPosition);
//为指定的轴设置实际(反馈)位置
//Motion.mAcm_AxSetActualPosition(m_Axishand[i], cmdPosition);
//Event
AxEnableEvtArray[i] |= (uint)EventType.EVT_AX_MOTION_DONE; //运动完成(减速直至停止)
AxEnableEvtArray[i] |= (uint)EventType.EVT_AX_VH_START; //轴加速到运行速度时
AxEnableEvtArray[i] |= (uint)EventType.EVT_AX_VH_END;//轴运行速度结束时,开始减速
//初次获取轴的运动I/O状态。
this.refreshAxisState(i);
}
//根据加载的文件设置设备的所有配置
string cfgPath = Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location) + "\\DevCfg\\Axis_" + DeviceNum + ".cfg";
if (File.Exists(cfgPath))
{
uResult = Motion.mAcm_DevLoadConfig(m_DeviceHandle, cfgPath);
if (uResult != (uint)ErrorCode.SUCCESS)
throw new Exception("Load Config Failed With Error Code: [0x" + Convert.ToString(uResult, 16) + "]");
}
uResult = Motion.mAcm_EnableMotionEvent(m_DeviceHandle, AxEnableEvtArray, GpEnableEvt, m_ulAxisCount, 3);
if (uResult != (uint)ErrorCode.SUCCESS)
throw new Exception("EnableMotionEvent Filed With Error Code[0x" + Convert.ToString(uResult, 16) + "]");
IsInit = true;
timer.Elapsed += Timer_Elapsed;
timer.Interval = 100;
timer.Enabled = true;
//用户应该创建一个新的线程来检查事件状态,例如:CheckEvtThread()函数
checkEventThread = new Thread(new ThreadStart(checkEvtThread));
checkEventThread.Start();
}
/// <summary>
/// 关闭设备
/// </summary>
/// <exception cref="Exception"></exception>
public void stop()
{
if (!IsInit) return;
uint i;
for (i = 0; i < m_ulAxisCount; i++)
{
if (AxState[i] == (uint)AxisState.STA_AX_ERROR_STOP)
{
log?.Invoke(1, i + "轴处于ErrorStop状态已重置");
//重置轴的状态。如果轴处于ErrorStop状态则调用此函数后状态将更改为Ready
Motion.mAcm_AxResetError(m_Axishand[i]);
}
// 命令轴减速停止(缓停)
Motion.mAcm_AxStopDec(m_Axishand[i]);
//sleep? 关闭电源使能,1: On
uint uResult = Motion.mAcm_AxSetSvOn(m_Axishand[i], 0);
if (uResult != (uint)ErrorCode.SUCCESS)
throw new Exception("Servo On Failed With Error Code: [0x" + Convert.ToString(uResult, 16) + "]");
}
//删除组中的所有轴并关闭组句柄
//Motion.mAcm_GpClose(ref m_GpHand);
//m_GpHand = IntPtr.Zero;
for (i = 0; i < m_ulAxisCount; i++)
{
//Close Axes
Motion.mAcm_AxClose(ref m_Axishand[i]);
}
timer.Elapsed -= Timer_Elapsed;
m_ulAxisCount = 0;
//Close Device
Motion.mAcm_DevClose(ref m_DeviceHandle);
m_DeviceHandle = IntPtr.Zero;
IsInit = false;
timer.Enabled = false;
}
/// <summary>
/// 缓停,jog时用
/// </summary>
public void stopDec(int axisIndex = -1)
{
for (int i = 0; i < m_ulAxisCount; i++)
{
if (i == axisIndex || axisIndex == -1)
{
Motion.mAcm_AxStopDec(m_Axishand[i]);
}
}
}
/// <summary>
/// 急停
/// </summary>
public void stop(int axisIndex = -1)
{
if (!IsInit) return;
for (int i = 0; i < m_ulAxisCount; i++)
{
if (i == axisIndex || axisIndex == -1)
{
Motion.mAcm_AxStopEmg(m_Axishand[i]);
}
}
}
public void resetAxisState(int axisIndex)
{
if (!IsInit) return;
if (AxState[axisIndex] == (uint)AxisState.STA_AX_ERROR_STOP)
{
//重置轴的状态。如果轴处于ErrorStop状态则调用此函数后状态将更改为Ready
Motion.mAcm_AxResetError(m_Axishand[axisIndex]);
}
// 命令轴减速停止(缓停)
Motion.mAcm_AxStopDec(m_Axishand[axisIndex]);
}
/// <summary>
/// 指定的轴设置命令位置
/// </summary>
public void resetCmdPosition(int axisIndex = -1, double position = 0)
{
if (!IsInit) return;
for (int i = 0; i < m_ulAxisCount; i++)
{
if (i == axisIndex || axisIndex == -1)
{
Motion.mAcm_AxSetCmdPosition(m_Axishand[i], position);
}
}
}
/// <summary>
/// 指定的轴设置实际(反馈)位置
/// </summary>
public void resetActualPosition(int axisIndex=-1, double position = 0)
{
if (!IsInit) return;
for (int i = 0; i < m_ulAxisCount; i++)
{
if (i == axisIndex || axisIndex == -1)
{
Motion.mAcm_AxSetActualPosition(m_Axishand[i], position);
}
}
}
/// <summary>
/// 获取速度 [vellow,velhigh,acc,dec,Jerk]
/// </summary>
/// <param name="axisIndex"></param>
/// <returns></returns>
public double[] getAxisVelParam(int axisIndex)
{
double[] value=new double[5];
Motion.mAcm_GetF64Property(m_Axishand[axisIndex], (uint)PropertyID.PAR_AxVelLow, ref value[0]);
Motion.mAcm_GetF64Property(m_Axishand[axisIndex], (uint)PropertyID.PAR_AxVelHigh, ref value[1]);
Motion.mAcm_GetF64Property(m_Axishand[axisIndex], (uint)PropertyID.PAR_AxAcc, ref value[2]);
Motion.mAcm_GetF64Property(m_Axishand[axisIndex], (uint)PropertyID.PAR_AxDec, ref value[3]);
Motion.mAcm_GetF64Property(m_Axishand[axisIndex], (uint)PropertyID.PAR_AxJerk, ref value[4]);//0-T/S 型曲线
return value;
}
/// <summary>
/// 速度设置 注运动的过程中可变速度加速度和减速度需使用AxChangeVelEx方法
/// </summary>
/// <param name="velLow">起始速度</param>
/// <param name="high">运行速度</param>
/// <param name="acc">加速度</param>
/// <param name="dec">减速度</param>
/// <param name="axisIndex"></param>
public void setAxisVelParam(double velLow, double high = 0, double acc = 0, double dec = 0, int axisIndex = -1)
{
uint result;
for (int i = 0; i < m_ulAxisCount; i++)
{
if (i == axisIndex || axisIndex == -1)
{
if ((AxisState)AxState[i] != AxisState.STA_AX_READY)
continue;
if (velLow > 0) result = Motion.mAcm_SetF64Property(m_Axishand[i], (uint)PropertyID.PAR_AxVelLow, velLow);
if (high > 0) result = Motion.mAcm_SetF64Property(m_Axishand[i], (uint)PropertyID.PAR_AxVelHigh, high);
if (acc > 0) result = Motion.mAcm_SetF64Property(m_Axishand[i], (uint)PropertyID.PAR_AxAcc, acc);
if (dec > 0) result = Motion.mAcm_SetF64Property(m_Axishand[i], (uint)PropertyID.PAR_AxDec, dec);
result = Motion.mAcm_SetF64Property(m_Axishand[i], (uint)PropertyID.PAR_AxJerk, 0);//0-T/S 型曲线
//Ret = Acm_SetF64Property(m_Axishand[0], PAR_AxVelLow, 2000); // 起始速度
//Ret = Acm_SetF64Property(m_Axishand[0], PAR_AxVelHigh, 8000); // 运行速度
//Ret = Acm_SetF64Property(m_Axishand[0], PAR_AxAcc, 10000); // 加速度
//Ret = Acm_SetF64Property(m_Axishand[0], PAR_AxDec, 10000); // 减速度
//Ret = Acm_SetF64Property(m_Axishand[0], PAR_AxJerk, 0); //0-T/S 型曲线
}
}
}
/// <summary>
/// 回HOME
/// </summary>
/// <param name="axisIndex"></param>
/// <param name="homeMode">16种回HOME模式0-15</param>
/// <param name="dir">0-正向 1-负向</param>
/// <exception cref="Exception"></exception>
public void home(int axisIndex = -1, uint homeMode = 11, uint dir = 1)
{
//研华运动控制卡共提供两个函数执行回Home Acm_AxHome 和Acm_AxMoveHome
//调用Acm_AxHome 执行回Home 时通过PAR_AxVelLow、PAR_AxVelHigh、PAR_AxAcc、 PAR_AxDec、PAR_AxJerk 设置初速度,运行速度、加速度、减速度、速度曲线类型。
//调用Acm_AxMoveHome 执行回Home 时通过PAR_AxHomeVelLow、PAR_AxHomeVelHigh、 PAR_AxHomeAcc、PAR_AxHomeDec、PAR_AxHomeJerk 设置初速度,运行速度、加速度、 减速度、速度曲线类型。
uint result;
for (int i = 0; i < m_ulAxisCount; i++)
{
if (i == axisIndex || axisIndex == -1)
{
if ((AxisState)AxState[i] != AxisState.STA_AX_READY)
continue;
result = Motion.mAcm_AxHome(m_Axishand[i], homeMode, dir);
if (result != (uint)ErrorCode.SUCCESS)
throw new Exception("AxHome Failed With Error Code: [0x" + Convert.ToString(result, 16) + "]");
}
}
}
/// <summary>
/// 点到点运动
/// </summary>
/// <param name="axisIndex"></param>
/// <param name="pos">PPU位置方向为正负值</param>
/// <param name="isAbs">true:绝对 false:相对</param>
public bool move_ptp(int axisIndex, double pos, bool isAbs)
{
uint result;
if ((AxisState)AxState[axisIndex] != AxisState.STA_AX_READY)
return false;
if (isAbs) //Start single axis's absolute position motion.
result = Motion.mAcm_AxMoveAbs(m_Axishand[axisIndex], pos);
else //Start single axis's relative position motion
result = Motion.mAcm_AxMoveRel(m_Axishand[axisIndex], pos);
if (result != (uint)ErrorCode.SUCCESS)
{
log?.Invoke(2, "PTP Move Failed With Error Code[0x" + Convert.ToString(result, 16) + "]");
return false;
}
return true;
}
#region JOG
public void openJogMode(int axisIndex)
{
if (!IsInit) return;
if ((AxisState)AxState[axisIndex] != AxisState.STA_AX_READY)
return;
uint result;
//启用/禁用外置硬盘模式.0: Disabled (stop command) 1: JOG Mode 2: MPG Mode
result = Motion.mAcm_AxSetExtDrive(m_Axishand[axisIndex], 0);
result = Motion.mAcm_AxSetExtDrive(m_Axishand[axisIndex], 1);
if (result != (uint)ErrorCode.SUCCESS)
throw new Exception("Start external driver Failed With Error Code[0x" + Convert.ToString(result, 16) + "]");
//设置外部驱动器的输入引脚
//0 轴 0(默认值) 仅支持 0
//1 轴 1(不支持)
//2 轴 2(不支持)
//3 轴 3(不支持)
result = Motion.mAcm_SetU32Property(m_Axishand[axisIndex], (uint)PropertyID.CFG_AxExtMasterSrc, 0);
if (result != (uint)ErrorCode.SUCCESS)
throw new Exception("Set Property-AxExtMasterSrc Failed With Error Code[0x" + Convert.ToString(result, 16) + "]");
//当启用外部驱动时。此属性允许通过数字输入通道选择驱动轴
result = Motion.mAcm_SetU32Property(m_Axishand[axisIndex], (uint)PropertyID.CFG_AxExtSelEnable, 1);
if (result != (uint)ErrorCode.SUCCESS && result != (uint)ErrorCode.PropertyIDNotSupport)//Added for Supporting PCI1245 and PCI1265
throw new Exception("Set Property-AxExtSelEnable Failed With Error Code[0x" + Convert.ToString(result, 16) + "]");
//理论脉冲数
result = Motion.mAcm_SetU32Property(m_Axishand[axisIndex], (uint)PropertyID.CFG_AxExtPulseNum, 1000);
if (result != (uint)ErrorCode.SUCCESS && result != (uint)ErrorCode.PropertyIDNotSupport)//Added for Supporting PCI1245 and PCI1265
throw new Exception("Set Property-CFG_AxExtPulseNum Failed With Error Code[0x" + Convert.ToString(result, 16) + "]");
}
public void closeJogMode(int axisIndex = -1)
{
if (!IsInit) return;
uint result;
for (int i = 0; i < m_ulAxisCount; i++)
{
if (i == axisIndex || axisIndex == -1)
{
axisIndex = i;
if ((AxisState)AxState[axisIndex] == AxisState.STA_AX_EXT_JOG)
{
//启用/禁用外置硬盘模式.0: Disabled (stop command) 1: JOG Mode 2: MPG Mode
result = Motion.mAcm_AxSetExtDrive(m_Axishand[axisIndex], 0);
//命令轴减速停止
result = Motion.mAcm_AxStopDec(m_Axishand[axisIndex]);
}
}
}
}
/// <summary>
/// jog运行
/// </summary>
/// <param name="axisIndex"></param>
/// <param name="dic">0正向1负向</param>
public void jog(int axisIndex, ushort dic)
{
//Jog 运动的方向0正向1负向
Motion.mAcm_AxJog(m_Axishand[axisIndex], dic);
}
#endregion
#region Private
private void Timer_Elapsed(object sender, ElapsedEventArgs e)
{
if (!IsInit) return;
for (int i = 0; i < m_ulAxisCount; i++)
refreshAxisState(i);
}
private void refreshAxisState(int AxisIndex)
{
uint result;
//获取指定轴的当前命令位置
if ((uint)ErrorCode.SUCCESS == Motion.mAcm_AxGetCmdPosition(m_Axishand[AxisIndex], ref CmdPos[AxisIndex]))
axisPosEvent?.Invoke(AxisIndex, AxisPosType.CmdPos, CmdPos[AxisIndex]);
//获取指定轴的当前实际(反馈)位置
if ((uint)ErrorCode.SUCCESS == Motion.mAcm_AxGetActualPosition(m_Axishand[AxisIndex], ref ActualPos[AxisIndex]))
axisPosEvent?.Invoke(AxisIndex, AxisPosType.ActualPos, ActualPos[AxisIndex]);
//获取轴的运动I/O状态。
if ((uint)ErrorCode.SUCCESS == Motion.mAcm_AxGetMotionIO(m_Axishand[AxisIndex], ref IOStatus[AxisIndex]))
axisStateEvent?.Invoke(AxisIndex, AxisStateType.AxisIOState, IOStatus[AxisIndex]);
//log?.Invoke(0, $"({AxisIndex}轴)AxisMotionIO = {((Ax_Motion_IO)IOStatus[AxisIndex]).ToString()}");
//checkMotionIOStatus(AxisIndex, IOStatus[AxisIndex]);
//获取Axis的当前状态
if ((uint)ErrorCode.SUCCESS == Motion.mAcm_AxGetState(m_Axishand[AxisIndex], ref AxState[AxisIndex]))
axisStateEvent?.Invoke(AxisIndex, AxisStateType.AxisState, AxState[AxisIndex]);
//log?.Invoke(0, $"({AxisIndex}轴)AxisState = {((AxisState)AxState[AxisIndex]).ToString()}");
//获取Axis的当前运动状态
if ((uint)ErrorCode.SUCCESS == Motion.mAcm_AxGetMotionStatus(m_Axishand[AxisIndex], ref AxMotionState[AxisIndex]))
axisStateEvent?.Invoke(AxisIndex, AxisStateType.AxisMotionState, AxMotionState[AxisIndex]);
//log?.Invoke(0, $"({AxisIndex}轴)AxisMotionStatus = {AxMotionState[AxisIndex].ToString()}");
}
private bool _ORG, _EL_R, _EL_L, _ALM, _SVON;
private void checkMotionIOStatus(int axisIndex, uint IOStatus)
{
if ((IOStatus & (uint)Ax_Motion_IO.AX_MOTION_IO_ALM) > 0)//报警信号输出
warningEvent?.Invoke(2, $"轴{axisIndex} 发出告警!!");
bool ALM = (IOStatus & (uint)Ax_Motion_IO.AX_MOTION_IO_ALM) > 0;
bool ORG = (IOStatus & (uint)Ax_Motion_IO.AX_MOTION_IO_ORG) > 0;//ORG
bool EL_R = (IOStatus & (uint)Ax_Motion_IO.AX_MOTION_IO_LMTP) > 0;//右极限
bool EL_L = (IOStatus & (uint)Ax_Motion_IO.AX_MOTION_IO_LMTN) > 0;//-EL 左
bool SVON = (IOStatus & (uint)Ax_Motion_IO.AX_MOTION_IO_SVON) > 0;
}
/// <summary>
/// 轴事件
/// </summary>
private void checkEvtThread()
{
uint Result;
UInt32[] AxEvtStatusArray = new UInt32[32];
UInt32[] GpEvtStatusArray = new UInt32[32];
UInt32 i;
while (IsInit)
{
//如果你想获得轴或组的事件状态,你应该通过调用 Motion.mAcm_EnableMotionEvent 来启用这些事件
//AxEvtStatusArray[n]返回每个轴的中断事件状态n 表示运动设备的轴个数
//GpEnableEvtArrayy[n]:返回每个群组的中断事件状态
//AxArrayElements U32 IN AxEvtStatusArray 中元素个数
//GpArrayElements U32 IN GpEvtStatusArray 中元素个数
//Millisecond U32 IN 设定每次Check 事件时的等待时间
Result = Motion.mAcm_CheckMotionEvent(m_DeviceHandle, AxEvtStatusArray, GpEvtStatusArray, m_ulAxisCount, 4, 4);//3,10
if (Result == (uint)ErrorCode.SUCCESS)
{
for (i = 0; i < m_ulAxisCount; i++)
{
if ((AxEvtStatusArray[i] & (uint)EventType.EVT_AX_MOTION_DONE) > 0)
{
//m_AxDoneEvtCnt[i]++;
}
if ((AxEvtStatusArray[i] & (uint)EventType.EVT_AX_VH_START) > 0)
{
//m_AxVHStartCnt[i]++;
}
if ((AxEvtStatusArray[i] & (uint)EventType.EVT_AX_VH_END) > 0)
{
//m_AxVHEndCnt[i]++;
}
}
//if (m_GpHand != IntPtr.Zero)
//{
// if (textBoxGpID.Text != "")
// {
// if ((GpEvtStatusArray[0] & ((uint)EventType.EVT_GP1_MOTION_DONE << Convert.ToByte(textBoxGpID.Text))) > 0)
// {
// m_GpDoneEvtCnt++;
// }
// if ((GpEvtStatusArray[1] & ((uint)EventType.EVT_GP1_VH_START << Convert.ToByte(textBoxGpID.Text))) > 0)
// {
// m_GpVHStartCnt++;
// }
// if ((GpEvtStatusArray[2] & ((uint)EventType.EVT_GP1_VH_END << Convert.ToByte(textBoxGpID.Text))) > 0)
// {
// m_GpVHEndCnt++;
// }
// }
//}
}
}
}
private string getErrInfo(uint errorCode)
{
StringBuilder ErrorMsg = new StringBuilder("", 100);
//Get the error message according to error code returned from API
Boolean res = Motion.mAcm_GetErrorMessage(errorCode, ErrorMsg, 100);
if (res) return ErrorMsg.ToString();
return "获取错误信息失败!";
}
#endregion
/*
[Category("HLMT")]
[Description("启用/禁用硬件限制信号.")]
public HLmtEnable ElEnable
{
get
{
if ((FtHELMap & 1) == 0)
{
return HLmtEnable.NOT_SUPPORT;
}
if (Handle != IntPtr.Zero)
{
uint BufferLength = 4u;
Motion.mAcm_GetProperty(Handle, 574u, ref m_ElEnable, ref BufferLength);
return (HLmtEnable)m_ElEnable;
}
return (HLmtEnable)m_ElEnable;
}
set
{
m_ElEnable = (uint)value;
if (Handle != IntPtr.Zero)
{
if (m_ElEnable != 2)
{
uint bufferLength = 4u;
result = Motion.mAcm_SetProperty(Handle, 574u, ref m_ElEnable, bufferLength);
if (result == 0)
{
designValue.ElEnable = value;
}
else if (result != 2147483658u && result != 2147504130u)
{
MessageBox.Show("Set ElEnable=" + ElEnable.ToString() + " failed with Error Code[0x" + Convert.ToString(result, 16) + "]:" + (ErrorCode)result, "Advantech Motion Component", MessageBoxButtons.OK, MessageBoxIcon.Hand, MessageBoxDefaultButton.Button1);
}
}
}
else
{
designValue.ElEnable = value;
}
}
}
[Category("HLMT")]
[Description("启用/禁用此轴的负硬件限制.")]
public HLmtEnable MelEnable
{
get
{
if ((FtHELMap & 1) == 0)
{
return HLmtEnable.NOT_SUPPORT;
}
if (Handle != IntPtr.Zero)
{
uint BufferLength = 4u;
Motion.mAcm_GetProperty(Handle, 758u, ref m_MelEnable, ref BufferLength);
return (HLmtEnable)m_MelEnable;
}
return (HLmtEnable)m_MelEnable;
}
set
{
m_MelEnable = (uint)value;
if (Handle != IntPtr.Zero)
{
if (m_MelEnable != 2)
{
uint bufferLength = 4u;
result = Motion.mAcm_SetProperty(Handle, 758u, ref m_MelEnable, bufferLength);
if (result == 0)
{
designValue.MelEnable = value;
}
else if (result != 2147483658u && result != 2147504130u)
{
MessageBox.Show("Set MelEnable=" + m_MelEnable.ToString() + " failed with Error Code[0x" + Convert.ToString(result, 16) + "]:" + (ErrorCode)result, "Advantech Motion Component", MessageBoxButtons.OK, MessageBoxIcon.Hand, MessageBoxDefaultButton.Button1);
}
}
}
else
{
designValue.MelEnable = value;
}
}
}
[Category("HLMT")]
[Description("启用/禁用此轴的正向硬件限制.")]
public HLmtEnable PelEnable
{
get
{
if ((FtHELMap & 1) == 0)
{
return HLmtEnable.NOT_SUPPORT;
}
if (Handle != IntPtr.Zero)
{
uint BufferLength = 4u;
Motion.mAcm_GetProperty(Handle, 757u, ref m_PelEnable, ref BufferLength);
return (HLmtEnable)m_PelEnable;
}
return (HLmtEnable)m_PelEnable;
}
set
{
m_PelEnable = (uint)value;
if (Handle != IntPtr.Zero)
{
if (m_PelEnable != 2)
{
uint bufferLength = 4u;
result = Motion.mAcm_SetProperty(Handle, 757u, ref m_PelEnable, bufferLength);
if (result == 0)
{
designValue.PelEnable = value;
}
else if (result != 2147483658u && result != 2147504130u)
{
MessageBox.Show("Set PelEnable=" + m_PelEnable.ToString() + " failed with Error Code[0x" + Convert.ToString(result, 16) + "]:" + (ErrorCode)result, "Advantech Motion Component", MessageBoxButtons.OK, MessageBoxIcon.Hand, MessageBoxDefaultButton.Button1);
}
}
}
else
{
designValue.PelEnable = value;
}
}
}
[Category("HLMT")]
[Description("为硬件限位信号设置活动逻辑.")]
public HLmtLogic ElLogic
{
get
{
if ((FtHELMap & 2) == 0)
{
return HLmtLogic.NOT_SUPPORT;
}
if (Handle != IntPtr.Zero)
{
uint BufferLength = 4u;
Motion.mAcm_GetProperty(Handle, 575u, ref m_ElLogic, ref BufferLength);
return (HLmtLogic)m_ElLogic;
}
return (HLmtLogic)m_ElLogic;
}
set
{
m_ElLogic = (uint)value;
if (Handle != IntPtr.Zero)
{
if (m_ElLogic != 2)
{
uint BufferLength = 4u;
result = Motion.mAcm_SetProperty(Handle, 575u, ref m_ElLogic, BufferLength);
if (result == 0)
{
designValue.ElLogic = value;
Motion.mAcm_GetProperty(Handle, 704u, ref m_PelLogic, ref BufferLength);
Motion.mAcm_GetProperty(Handle, 705u, ref m_MelLogic, ref BufferLength);
}
else if (result != 2147483658u && result != 2147504130u)
{
MessageBox.Show("Set ElLogic=" + m_ElLogic.ToString() + " failed with Error Code[0x" + Convert.ToString(result, 16) + "]:" + (ErrorCode)result, "Advantech Motion Component", MessageBoxButtons.OK, MessageBoxIcon.Hand, MessageBoxDefaultButton.Button1);
}
}
}
else
{
designValue.ElLogic = value;
}
}
}
*/
}
}