[英]C# multi-threading in RFID readers
我写了一个程序可以连接到多个 RFID 阅读器并同时开始检测标签。 但是因为他们都在 UI-Thread(主线程)上工作,每次我添加新阅读器时,我的 UI 和阅读 function 都会变慢......我需要为每个阅读器创建一个新线程并让该阅读器与新的工作线程。 但是我不知道在我的 c# 程序中我在哪里导入了新的 Thread() function。 我有一个用于读取标签的 windows 表单计时器。 我只是更改了我的程序,为每个读者创建了一个 bgWorker。 我删除了我的计时器。 我使用 while 循环进行阅读。 但是每次我添加一个新的阅读器并且它开始读取标签时,尽管它正在使用一个新的工作线程 ID 但其他阅读器的阅读功能变得更慢
public partial class frmMain : Form
{
public frmMain()
{
InitializeComponent();
}
private void frmMain_Load(object sender, EventArgs e)
{
int count = 9;
for (int i = 0; i < count; i++)
{
RfControl rfc = new RfControl();
rfc.gTitle.Text = "Device" + Convert.ToString((i + 1));
this.flowLayoutPanel1.Controls.Add(rfc);
}
}
private void frmMain_FormClosing(object sender, FormClosingEventArgs e)
{
for(int i=0; i<this.flowLayoutPanel1.Controls.Count; i++)
{
RfControl rfc = (RfControl)this.flowLayoutPanel1.Controls[i];
}
}
}
public partial class RfControl : UserControl
{
RfReader rf = new RfReader();
public RfControl()
{
InitializeComponent();
}
private void btnOpen_Click(object sender, EventArgs e)
{
try
{
rf.type = this.cbType.Text;
rf.IPAddr = this.txtIP.Text.Trim();
rf.port = Convert.ToInt32(this.txtPort.Text.Trim());
rf.OnScan += new EventHandler(rf_OnScan);
rf.Open();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message);
}
}
void rf_OnScan(object sender, EventArgs e)
{
try
{
string value = ((RfReader)sender).value;
if (this.lstContent.Items.IndexOf(value) == -1)
{
this.lstContent.Items.Add(value);
}
this.txtCount.Text = this.lstContent.Items.Count.ToString();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message);
}
}
private void btnClose_Click(object sender, EventArgs e)
{
try
{
rf.Close();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message);
}
}
private void btnClear_Click(object sender, EventArgs e)
{
this.lstContent.Items.Clear();
this.txtCount.Text = "0";
}
private void btnQuery_Click(object sender, EventArgs e)
{
rf.bgWorker.RunWorkerAsync();
}
}
class RfReader
{
Api api = new Api();
ArrayList idList = new ArrayList();
byte[,] tagData = null;
byte v1 = 0;
byte v2 = 0;
int status = 0;
int iMembankMask = 0, iStartAddr_Reserve = 0, iStartAddr_EPC, iStartAddr_TID, iStartAddr_User, reserveLen, epcLen, tidLen, userLen, readCnt, wordLen = 0;
public int frmcomportindex;
public byte readerAddr = 0xff;
private byte fComAdr = 0xff;
public int port = -1, openresult = 0;
public string IPAddr = "";
public string type = "";
public string value = "";
public string X = "";
public string Y = "";
public string Name = "";
public System.Windows.Forms.Timer timer = null;
public BackgroundWorker bgWorker = null;
public RfReader()
{
bgWorker = new BackgroundWorker();
bgWorker.DoWork += new DoWorkEventHandler(timer_Tick);
}
void timer_Tick(object sender, EventArgs e)
{
while (true)
{
Reader();
}
}
public void Open()
{
if (type == "AR")
{
if (!api.isNetWorkConnect(IPAddr))
{
api.TcpCloseConnect();
throw new Exception(IPAddr + " Open failed");
}
status = api.TcpConnectReader(IPAddr, Convert.ToInt32(port));
if (status != ReaderApi.Api.SUCCESS_RETURN)
{
api.TcpCloseConnect();
throw new Exception(IPAddr + " Open failed");
}
status = api.GetFirmwareVersion(255, ref v1, ref v2);
if (status != ReaderApi.Api.SUCCESS_RETURN)
{
api.TcpCloseConnect();
throw new Exception(IPAddr + " Open failed");
}
iStartAddr_Reserve = iStartAddr_EPC = iStartAddr_TID = iStartAddr_User = reserveLen = epcLen = tidLen = userLen = readCnt = 0;
iMembankMask = 0;
wordLen = 6;
iMembankMask += 1;
wordLen += 4;
iStartAddr_Reserve = 0;
reserveLen = 4;
iMembankMask += 2;
wordLen += 8;
iStartAddr_EPC = 0;
epcLen = 8;
iMembankMask += 4;
wordLen += 12;
iStartAddr_TID = 0;
tidLen = 12;
iMembankMask += 8;
wordLen += 10;
iStartAddr_User = 0;
userLen = 10;
tagData = new byte[500, wordLen * 4];
idList.Clear();
throw new Exception(IPAddr + " Open Success");
}
else if (type == "ZK")
{
byte readerAddr = Convert.ToByte("FF", 16); // $FF;
openresult = StaticClassReaderB.OpenNetPort(port, IPAddr, ref fComAdr, ref frmcomportindex);
if ((openresult == 0x35) || (openresult == 0x30))
{
StaticClassReaderB.CloseNetPort(frmcomportindex);
throw new Exception(IPAddr + " Open failed");
}
if (openresult == 0)
{
throw new Exception(IPAddr + " Open Success");
}
}
}
public void Close()
{
if (type == "AR")
{
api.TcpCloseConnect();
}
else if (type == "ZK")
{
StaticClassReaderB.CloseNetPort(frmcomportindex);
frmcomportindex = -1;
}
}
public event EventHandler OnScan;
public void Reader()
{
if (type == "AR")
{
readCnt = 0;
int getCount = 0;
string strTemp = "", strAnteNo = "", strEPC = "", strSubEPC = "", strTID = "", strReserve = "", strUser = "";
status = api.Gen2MultiTagRead(255, (byte)iMembankMask, (byte)iStartAddr_Reserve, (byte)reserveLen, (byte)iStartAddr_EPC, (byte)epcLen, (byte)iStartAddr_TID, (byte)tidLen, (byte)iStartAddr_User, (byte)userLen, ref readCnt);
if (status == Api.SUCCESS_RETURN)
{
if (readCnt > 0)
{
if (api.GetTagData(255, ref tagData, readCnt, ref getCount) == Api.SUCCESS_RETURN && getCount > 0)
{
for (int loop = 0; loop < getCount; loop++)
{
strTemp = "";
for (int j = 1; j <= (int)tagData[loop, 0]; j++)
strTemp += string.Format("{0:X2}", tagData[loop, j]);
strEPC = strTemp.Substring(2, 24);
strReserve = strTemp.Substring(26, reserveLen * 4);
strSubEPC = strTemp.Substring(26 + reserveLen * 4, epcLen * 4);
value = strTemp.Substring((26 + reserveLen * 4 + epcLen * 4) + 8, 16);
strUser = strTemp.Substring(26 + reserveLen * 4 + epcLen * 4 + tidLen * 4, userLen * 4);
//OnScan(this, new EventArgs());
}
}
}
}
}
else if (type == "ZK")
{
int CardNum = 0, Totallen = 0, EPClen, m, CardIndex;
byte[] EPC = new byte[5000];
string temps, s;
byte AdrTID = 0, LenTID = 0, TIDFlag = 0;
AdrTID = 2;
LenTID = 4;
TIDFlag = 1;
byte Qvalue = 4;
byte Session = 0;
string lastEPC = "";
int fCmdRet = StaticClassReaderB.Inventory_G2(ref fComAdr, Qvalue, Session, AdrTID, LenTID, TIDFlag, EPC, ref Totallen, ref CardNum, frmcomportindex);
if ((fCmdRet == 1) | (fCmdRet == 2) | (fCmdRet == 3) | (fCmdRet == 4) | (fCmdRet == 0xFB))//The search is over
{
if (CardNum == 0)
{
return;
}
byte[] daw = new byte[Totallen];
Array.Copy(EPC, daw, Totallen);
temps = ByteArrayToHexString(daw);
if (temps == "") return;
m = 0;
for (CardIndex = 0; CardIndex < CardNum; CardIndex++)
{
EPClen = daw[m];
string TID = temps.Substring(m * 2 + 2, EPClen * 2);
lastEPC = TID;
m = m + EPClen + 2;
value = TID;
}
}
}
}
}
使用 Thread-Class 而不是 BgWorker 并调用所有 UI-Access。 仅在访问 UI 元素时执行调用,如果执行 rfid 阅读器操作则不要调用。 永远不要使用计时器来完成您已经理解的此类工作。 如果您需要更多帮助,请通过联系表与我联系
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.