using Aurora.Api;
using Hermes;
using Newtonsoft.Json.Linq;
using System;
using System.Collections.Generic;
using System.IO.Ports;
using System.Linq;
using System.Runtime.Remoting.Channels;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
namespace VisionLight
{
///
/// Inkjet oleds 에서 검증 - LightLTPS
/// Serial connection type
#warning [TODO : Aurora 고정부 추가후 수정 필요]
///
internal class Light_LVS_PT0105_raw : LightBase_Serial
{
public Light_LVS_PT0105_raw(string deviceId) : base(deviceId)
{
DeviceId = deviceId;
LOG = new Logger(deviceId);
}
#region Implement Base interface & methods
protected override int DoActivate(IDeviceConfig config)
{
if (IsSimul)
return E1.OK;
#warning [TODO : Aurora 고정부 추가후 수정 필요]
//SerialPort.DataReceived += SerialPort_DataReceived;
return base.DoActivate(config);
}
protected override int DoDeactivate()
{
#warning [TODO : Aurora 고정부 추가후 수정 필요]
//SerialPort.DataReceived -= SerialPort_DataReceived;
return base.DoDeactivate();
}
protected override eLightResult SetLevelImpl(int level, int channel)
{
return SetLightValue(channel, level) ? eLightResult.OK : eLightResult.NG;
}
protected override eLightResult SetOffImpl(int channel)
{
return SetLightOnOff(channel, false) ? eLightResult.OK : eLightResult.NG;
}
protected override eLightResult SetOnImpl(int channel)
{
return SetLightOnOff(channel, true) ? eLightResult.OK : eLightResult.NG;
}
#endregion
#region fields
const byte CR = 0x0D;
const byte LF = 0x0A;
const byte ACK = 0x06;
const byte NAK = 0x15;
int _ReceiveSize = 0;
string _ValueBuff;
#endregion
Queue _DataQueue;
public Queue GetDataQueue => _DataQueue;
private bool SetLightValue(int nChannel, int nValue)
{
if (!IsSimul)
{
if (!SerialConn.IsPortOpen())
return false;
}
//ReceiveStatusMsgAck = false;
byte[] bySend = new byte[] { (byte)':', (byte)'1', (byte)'1', (byte)'0', (byte)'0', (byte)'0', (byte)'0', CR, LF };
nValue = Math.Min(Math.Max(nValue, 0), 9999);
string strBuf = string.Format("{0:X1}", nChannel + 1);
bySend[2] = (byte)strBuf[0];
//string strBuf = string.Format("{0:0000}", nValue);
strBuf = string.Format("{0:D4}", nValue);
bySend[3] = (byte)strBuf[0];
bySend[4] = (byte)strBuf[1];
bySend[5] = (byte)strBuf[2];
bySend[6] = (byte)strBuf[3];
bool bError = false;
try
{
for (int i = 0; i < 3; i++)
{
bError = false;
_DataQueue.Clear();
SerialConn.Write(bySend);
DateTime startTime = DateTime.Now;
TimeSpan timeSpan;
_ReceiveSize = 0;
while (true)
{
Thread.Sleep(1);
DateTime currentTime = DateTime.Now;
timeSpan = currentTime - startTime;
if (timeSpan.TotalSeconds > 3.0)
{
bError = true;
LOG.D("Receive Msg Timeout");
break;
}
if (ReadAck())
{
break;
}
}
if (bError == false)
break;
}
}
catch (UnauthorizedAccessException)
{
//Console.WriteLine("시리얼 포트에 액세스할 권한이 없습니다.");
return false;
}
catch (System.IO.IOException)
{
//Console.WriteLine("시리얼 포트를 열 수 없습니다.");
return false;
}
catch (Exception ex)
{
LOG.W("Warning : " + ex.Message, "SetLightValue");
//Console.WriteLine("오류 발생: " + ex.Message);
return false;
}
return bError ? false : true;
}
private bool SetLightOnOff(int nChannel, bool bOn)
{
if (!IsSimul)
{
if (!SerialConn.IsPortOpen())
return false;
}
//ReceiveStatusMsgAck = false;
byte[] bySend = new byte[] { (byte)':', (byte)'1', (byte)'O', (byte)'0', CR, LF };
string strBuf = string.Format("{0:X}", bOn ? (nChannel + 1) : 0);
bySend[3] = (byte)strBuf[0];
bool bError = false;
try
{
for (int i = 0; i < 3; i++)
{
bError = false;
_DataQueue.Clear();
SerialConn.Write(bySend);
DateTime startTime = DateTime.Now;
TimeSpan timeSpan;
while (true)
{
Thread.Sleep(1);
DateTime currentTime = DateTime.Now;
timeSpan = currentTime - startTime;
if (timeSpan.TotalSeconds > 3.0)
{
bError = true;
LOG.D("Receive Msg Timeout");
break;
}
if (ReadAck())
{
break;
}
}
if (bError == false)
break;
}
}
catch (UnauthorizedAccessException)
{
//Console.WriteLine("시리얼 포트에 액세스할 권한이 없습니다.");
return false;
}
catch (System.IO.IOException)
{
//Console.WriteLine("시리얼 포트를 열 수 없습니다.");
return false;
}
catch (Exception ex)
{
LOG.W("Warning : " + ex.Message, "SetLightOnOff");
//Console.WriteLine("오류 발생: " + ex.Message);
return false;
}
return bError ? false : true;
}
public bool GetLightValue(int nChannel, ref int nValue)
{
if (!IsSimul)
{
if (!SerialConn.IsPortOpen())
return false;
}
//ReceiveStatusMsgValue = false;
byte[] bySend = new byte[] { (byte)':', (byte)'R', (byte)'1', CR, LF };
string strBuf = string.Format("{0:X1}", nChannel + 1);
bySend[2] = (byte)strBuf[0];
bool bError = false;
try
{
for (int i = 0; i < 3; i++)
{
bError = false;
_DataQueue.Clear();
SerialConn.Write(bySend);
DateTime startTime = DateTime.Now;
TimeSpan timeSpan;
_ReceiveSize = 0;
string value = string.Empty;
_ValueBuff = string.Empty;
while (true)
{
Thread.Sleep(1);
DateTime currentTime = DateTime.Now;
timeSpan = currentTime - startTime;
if (timeSpan.TotalSeconds > 3.0)
{
bError = true;
LOG.D("Receive Msg Timeout");
break;
}
if (ReadValue(ref value))
{
//nValue = int.Parse(value);
int nChNum = 0;
int nLightVal = 0;
GetChNumAndLightVal(value, ref nChNum, ref nLightVal);
nValue = nLightVal;
break;
}
}
if (bError == false)
break;
}
}
catch (UnauthorizedAccessException)
{
//Console.WriteLine("시리얼 포트에 액세스할 권한이 없습니다.");
return false;
}
catch (System.IO.IOException)
{
//Console.WriteLine("시리얼 포트를 열 수 없습니다.");
return false;
}
catch (Exception ex)
{
LOG.W("Warning : " + ex.Message, "GetLightValue");
//Console.WriteLine("오류 발생: " + ex.Message);
return false;
}
return bError ? false : true;
}
private void GetChNumAndLightVal(string value, ref int nChNum, ref int nLightVal)
{
int[] ascii_ch = new int[1];
int[] ascii_value = new int[4];
ascii_ch[0] = int.Parse(value.Substring(5, 2));
ascii_value[0] = int.Parse(value.Substring(13, 2));
ascii_value[1] = int.Parse(value.Substring(15, 2));
ascii_value[2] = int.Parse(value.Substring(17, 2));
ascii_value[3] = int.Parse(value.Substring(19, 2));
char[] cChnum = new char[1];
cChnum[0] = (char)ascii_ch[0];
char[] cLightVal = new char[4];
cLightVal[0] = (char)ascii_value[0];
cLightVal[1] = (char)ascii_value[1];
cLightVal[2] = (char)ascii_value[2];
cLightVal[3] = (char)ascii_value[3];
nChNum = Convert.ToInt32(new string(cChnum));
nChNum -= 1; // ch no은 0-base
nLightVal = Convert.ToInt32(new string(cLightVal));
}
private bool ReadAck()
{
byte byReadCommand = new byte();
if (_DataQueue.Count > 0)
{
byReadCommand = _DataQueue.Dequeue();
_ReceiveSize++;
}
if ((_ReceiveSize != 0) && byReadCommand == ACK)
return true;
if (_ReceiveSize >= 1)
return true;
return false;
}
private bool ReadValue(ref string value)
{
if (_DataQueue.Count > 0)
{
_ValueBuff += _DataQueue.Dequeue();
_ReceiveSize++;
}
//if (strValueBuff.IndexOf('\n') != -1)
if (_ValueBuff.IndexOf((char)LF) != -1)
{
value = _ValueBuff.Substring(6);
return true;
}
if (_ReceiveSize > 9)
{
value = _ValueBuff/*.Substring(6)*/;
return true;
}
return false;
}
private void SerialPort_DataReceived(object sender, SerialDataReceivedEventArgs e)
{
//Serial 통신 Read Data
#warning [TODO: Aurora 고정부 추가후 수정 필요]
int dataLength = (sender as SerialPort).BytesToRead;// _SerialPort.BytesToRead;
byte[] byBuffer = new byte[dataLength];
SerialConn.Read(byBuffer);
for (int i = 0; i < dataLength; i++)
{
_DataQueue.Enqueue(byBuffer[i]);
}
}
}
}