版博士V2.0程序
Вы не можете выбрать более 25 тем Темы должны начинаться с буквы или цифры, могут содержать дефисы(-) и должны содержать не более 35 символов.
 
 
 
 

702 строки
28 KiB

  1. using System;
  2. using System.Collections.Generic;
  3. using System.Diagnostics;
  4. using System.Drawing;
  5. using System.Drawing.Imaging;
  6. using System.IO;
  7. using System.Linq;
  8. using System.Reflection;
  9. using System.Threading;
  10. using System.Threading.Tasks;
  11. using MaiMuAOI.SysCtrl;
  12. using MaiMuControl.Device;
  13. using Microsoft.ML.OnnxRuntime;
  14. using Microsoft.ML.OnnxRuntime.Tensors;
  15. using OpenCvSharp;
  16. using Yolo5;
  17. namespace MaiMuAOI.ImageProcessing
  18. {
  19. public class DefectLib : IDisposable
  20. {
  21. public Action<WarningEnum, string> WarningEvent;
  22. /// <summary>
  23. /// 检测结果JSON(原图,结果)
  24. /// </summary>
  25. public Action<DefectTask> finishEvent;
  26. /// <summary>
  27. /// 是否打开设备成功
  28. /// </summary>
  29. public bool IsInit { get; private set; } = false;
  30. //private System.Timers.Timer timer = new System.Timers.Timer();
  31. private Yolo_Class yolo1;
  32. private InferenceSession _onnxSession;
  33. private Yolo_Class yolo2;
  34. private InferenceSession _onnxSession2;
  35. private Yolo_Class yolo3;
  36. private InferenceSession _onnxSession3;
  37. //
  38. private Thread t_task, t_task_operation, t_task_operation2, t_task_operation3, t_task_tag;
  39. //=======task list
  40. private List<DefectTask> taskList = new List<DefectTask>();
  41. private List<DefectTask> taskOperationList = new List<DefectTask>();
  42. private List<DefectTask> taskTagList = new List<DefectTask>();
  43. public DefectLib()
  44. {
  45. }
  46. public bool start()
  47. {
  48. try
  49. {
  50. yolo1 = new Yolo_Class();
  51. yolo2 = new Yolo_Class();
  52. yolo3 = new Yolo_Class();
  53. //加载模型(只加载一次即可)
  54. //string modelFilePath = Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location) + "\\DevCfg\\best.onnx";
  55. //_onnxSession = yolo1.LoadModel(modelFilePath, true);//false-CPU true-显卡
  56. IsInit = true;
  57. //timer.Elapsed += Timer_Elapsed;
  58. //timer.Interval = 100;
  59. //timer.Enabled = true;
  60. taskList.Clear();
  61. taskOperationList.Clear();
  62. taskTagList.Clear();
  63. t_task = new System.Threading.Thread(runStep);
  64. t_task.IsBackground = true;
  65. t_task.Start();
  66. t_task_operation = new System.Threading.Thread(run2);
  67. t_task_operation.IsBackground = true;
  68. t_task_operation.Start();
  69. t_task_operation2 = new System.Threading.Thread(run3);
  70. t_task_operation2.IsBackground = true;
  71. t_task_operation2.Start();
  72. t_task_operation3 = new System.Threading.Thread(run4);
  73. t_task_operation3.IsBackground = true;
  74. t_task_operation3.Start();
  75. return true;
  76. }
  77. catch (Exception ex)
  78. {
  79. WarningEvent?.Invoke(WarningEnum.High, ex.Message);
  80. return false;
  81. }
  82. }
  83. public void stop()
  84. {
  85. if (!IsInit) return;
  86. try
  87. {
  88. IsInit = false;
  89. //timer.Elapsed -= Timer_Elapsed;
  90. //释放模型
  91. if (_onnxSession != null)
  92. {
  93. _onnxSession.Dispose();
  94. _onnxSession = null;
  95. }
  96. if (_onnxSession2 != null)
  97. {
  98. _onnxSession2.Dispose();
  99. _onnxSession2 = null;
  100. }
  101. if (_onnxSession3 != null)
  102. {
  103. _onnxSession3.Dispose();
  104. _onnxSession3 = null;
  105. }
  106. _preLoadONNXFilePath = null;
  107. if (t_task != null)
  108. {
  109. bool b = t_task.Join(5000);
  110. if (!b) t_task.Abort();
  111. t_task = null;
  112. }
  113. if (t_task_operation != null)
  114. {
  115. bool b = t_task_operation.Join(5000);
  116. if (!b) t_task_operation.Abort();
  117. t_task_operation = null;
  118. }
  119. if (t_task_operation2 != null)
  120. {
  121. bool b = t_task_operation2.Join(5000);
  122. if (!b) t_task_operation2.Abort();
  123. t_task_operation2 = null;
  124. }
  125. if (t_task_operation3 != null)
  126. {
  127. bool b = t_task_operation3.Join(5000);
  128. if (!b) t_task_operation3.Abort();
  129. t_task_operation3 = null;
  130. }
  131. if (t_task_tag != null)
  132. {
  133. bool b = t_task_tag.Join(5000);
  134. if (!b) t_task_tag.Abort();
  135. t_task_tag = null;
  136. }
  137. taskList.Clear();
  138. taskOperationList.Clear();
  139. taskTagList.Clear();
  140. }
  141. catch { }
  142. }
  143. private string _preLoadONNXFilePath;//记录上次成功加载的模型,不重复加载
  144. public void loadModelFile(string onnxFilePath)
  145. {
  146. //string modelFilePath = Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location) + "\\DevCfg\\best.onnx";
  147. //不重复加载
  148. if (!string.IsNullOrWhiteSpace(_preLoadONNXFilePath) && _preLoadONNXFilePath.ToLower() == onnxFilePath.ToLower())
  149. return;
  150. //Task.Run(async () =>
  151. //{
  152. // if (_onnxSession != null)
  153. // {
  154. // _onnxSession.Dispose();
  155. // _onnxSession = null;
  156. // }
  157. // _onnxSession = yolo1.LoadModel(onnxFilePath, true);//false-CPU true-显卡
  158. // _preLoadONNXFilePath = onnxFilePath;
  159. //});
  160. if (_onnxSession != null)
  161. {
  162. _onnxSession.Dispose();
  163. _onnxSession = null;
  164. }
  165. _onnxSession = yolo1.LoadModel(onnxFilePath, true);//false-CPU true-显卡
  166. if (_onnxSession2 != null)
  167. {
  168. _onnxSession2.Dispose();
  169. _onnxSession2 = null;
  170. }
  171. _onnxSession2 = yolo2.LoadModel(onnxFilePath, true);//false-CPU true-显卡
  172. if (_onnxSession3 != null)
  173. {
  174. _onnxSession3.Dispose();
  175. _onnxSession3 = null;
  176. }
  177. _onnxSession3 = yolo3.LoadModel(onnxFilePath, true);//false-CPU true-显卡
  178. _preLoadONNXFilePath = onnxFilePath;
  179. }
  180. /// <summary>
  181. /// 保存图片
  182. /// </summary>
  183. /// <param name="Img"></param>图片
  184. /// <param name="pictureUrl"></param>保存路径
  185. /// <param name="pictureName"></param>保存名称
  186. private void SaveImage(Bitmap Img, string pictureUrl, string pictureName)
  187. {
  188. if (!Directory.Exists(pictureUrl))
  189. {
  190. Directory.CreateDirectory(pictureUrl);
  191. }
  192. FileInfo FileUrl = new FileInfo(pictureUrl);//防止路径中有日期导致路径错误
  193. try
  194. {
  195. using (Bitmap bitmap = new Bitmap(Img))
  196. {
  197. using (MemoryStream stream = new MemoryStream())
  198. {
  199. bitmap.Save(stream, ImageFormat.Bmp);
  200. System.Drawing.Image img = System.Drawing.Image.FromStream(stream);
  201. //img.Save(FileUrl +"\\"+ pictureName);
  202. //img.Dispose();
  203. string szURL = FileUrl + "\\" + pictureName;
  204. img.Save(szURL, ImageFormat.Bmp);
  205. img.Dispose();
  206. }
  207. }
  208. }
  209. catch (Exception)
  210. {
  211. if (Img != null)
  212. {
  213. Img.Dispose();
  214. }
  215. }
  216. }
  217. private void runStep()
  218. {
  219. while (IsInit)
  220. {
  221. if (taskList.Count < 1 || _onnxSession == null)
  222. {
  223. Thread.Sleep(5);
  224. continue;
  225. }
  226. //
  227. var task = pop();
  228. try
  229. {
  230. if (task != null)
  231. {
  232. Stopwatch stopwatch = Stopwatch.StartNew();
  233. //源图
  234. //Bitmap bmp = yolo1.Read2Bmp(file_path);
  235. //切割图像,输入图像格式14208*10640
  236. stopwatch.Start();
  237. task.bmps_cut = yolo1.OpenCVToCutsMat(task.bmp, task.cut_size.Width, task.cut_size.Height);
  238. stopwatch.Stop();
  239. task.stopwatch[0] = stopwatch.ElapsedMilliseconds;
  240. //Resize图像
  241. stopwatch.Restart();
  242. task.bmps_resize = yolo1.OpenCVToResizesMat(task.bmps_cut, task.resize.Width, task.resize.Height);
  243. stopwatch.Stop();
  244. task.stopwatch[1] = stopwatch.ElapsedMilliseconds;
  245. //预处理模型
  246. stopwatch.Restart();
  247. task.tensors = yolo1.PreprocessImageMat(task.bmps_resize);
  248. stopwatch.Stop();
  249. task.stopwatch[2] = stopwatch.ElapsedMilliseconds;
  250. lock (taskOperationList)
  251. taskOperationList.Add(task);
  252. }
  253. Thread.Sleep(5);
  254. }
  255. catch (Exception ex)
  256. {
  257. WarningEvent?.Invoke(WarningEnum.Low, "DefectLib task1 err:" + ex.Message);
  258. task.isSucceed = false;
  259. task.resultInfo = ex.Message;
  260. callback(task);
  261. }
  262. }
  263. }
  264. private void run2()
  265. {
  266. while (IsInit)
  267. {
  268. if (taskOperationList.Count < 1)
  269. {
  270. Thread.Sleep(5);
  271. continue;
  272. }
  273. //
  274. var task = pop2();
  275. int liStep = 0;
  276. try
  277. {
  278. if (task != null)
  279. {
  280. Stopwatch stopwatch = Stopwatch.StartNew();
  281. //====运行推理(必需单队列)
  282. stopwatch.Start();
  283. IDisposableReadOnlyCollection<DisposableNamedOnnxValue>[] results = yolo1.RunModlel(_onnxSession, task.tensors);
  284. liStep = 1;
  285. task.informationList = yolo1.ScreeningResults_YD(results, task.bmps_resize, task.thresholds, task.thresholdsClass, task.recAreaThreshold);
  286. liStep = 2;
  287. //当前大图上缺陷个数
  288. int currPicDefectCount = 0;
  289. for (int x = 0; x < task.informationList.Count(); x++)
  290. currPicDefectCount += task.informationList[x].Count();
  291. task.defectCount = currPicDefectCount;
  292. stopwatch.Stop();
  293. task.stopwatch[3] = stopwatch.ElapsedMilliseconds;
  294. liStep = 3;
  295. if (task.informationList.Count > 0)
  296. {
  297. liStep = 4;
  298. //lock (taskTagList)
  299. // taskTagList.Add(task);
  300. //====打标 ,有缺陷返回缺陷图片数组,没缺陷返回所有图片数组
  301. stopwatch.Restart();
  302. task.bmps_tag = yolo1.DrawYoloPrediction2Mat(task.bmps_cut, task.informationList, 27, SixLabors.ImageSharp.Color.OrangeRed, task.resize.Width,
  303. task.Xmm, task.Ymm, out task.defectInfor2RestorationDesk);
  304. liStep = 5;
  305. if (ConfMgr.Instance.SysConfigParams.OpenFlawDistribution)
  306. {
  307. //大图缺陷坐标转换到图纸坐标
  308. if (!string.IsNullOrWhiteSpace(task.drawingPagePath) && task.defectInfor2RestorationDesk != null && task.defectInfor2RestorationDesk.Count > 0)
  309. task.defectInfor2RestorationDeskPage = yolo1.DefectDrawGerberImage(task.drawingPagePath, task.defectInfor2RestorationDesk);
  310. }
  311. stopwatch.Stop();
  312. task.stopwatch[4] = stopwatch.ElapsedMilliseconds;
  313. liStep = 6;
  314. task.bmpCompress = yolo1.ResizesMat_4(task.bmp);
  315. task.isSucceed = true;
  316. callback(task);
  317. }
  318. else
  319. {
  320. task.isSucceed = true;
  321. callback(task);
  322. }
  323. }
  324. Thread.Sleep(5);
  325. }
  326. catch (Exception ex)
  327. {
  328. WarningEvent?.Invoke(WarningEnum.Low, $"DefectLib task2 err({liStep}):" + ex.Message);
  329. task.isSucceed = false;
  330. task.resultInfo = ex.Message;
  331. callback(task);
  332. }
  333. }
  334. }
  335. private void run3()
  336. {
  337. while (IsInit)
  338. {
  339. if (taskOperationList.Count < 1)
  340. {
  341. Thread.Sleep(5);
  342. continue;
  343. }
  344. //
  345. var task = pop2();
  346. int liStep = 0;
  347. try
  348. {
  349. if (task != null)
  350. {
  351. Stopwatch stopwatch = Stopwatch.StartNew();
  352. //====运行推理(必需单队列)
  353. stopwatch.Start();
  354. IDisposableReadOnlyCollection<DisposableNamedOnnxValue>[] results = yolo2.RunModlel(_onnxSession2, task.tensors);
  355. liStep = 1;
  356. task.informationList = yolo2.ScreeningResults_YD(results, task.bmps_resize, task.thresholds, task.thresholdsClass, task.recAreaThreshold);
  357. liStep = 2;
  358. //当前大图上缺陷个数
  359. int currPicDefectCount = 0;
  360. for (int x = 0; x < task.informationList.Count(); x++)
  361. currPicDefectCount += task.informationList[x].Count();
  362. task.defectCount = currPicDefectCount;
  363. stopwatch.Stop();
  364. task.stopwatch[3] = stopwatch.ElapsedMilliseconds;
  365. liStep = 3;
  366. if (task.informationList.Count > 0)
  367. {
  368. liStep = 4;
  369. //lock (taskTagList)
  370. // taskTagList.Add(task);
  371. //====打标 ,有缺陷返回缺陷图片数组,没缺陷返回所有图片数组
  372. stopwatch.Restart();
  373. task.bmps_tag = yolo2.DrawYoloPrediction2Mat(task.bmps_cut, task.informationList, 27, SixLabors.ImageSharp.Color.OrangeRed, task.resize.Width,
  374. task.Xmm, task.Ymm, out task.defectInfor2RestorationDesk);
  375. liStep = 5;
  376. if (ConfMgr.Instance.SysConfigParams.OpenFlawDistribution)
  377. {
  378. //大图缺陷坐标转换到图纸坐标
  379. if (!string.IsNullOrWhiteSpace(task.drawingPagePath) && task.defectInfor2RestorationDesk != null && task.defectInfor2RestorationDesk.Count > 0)
  380. task.defectInfor2RestorationDeskPage = yolo2.DefectDrawGerberImage(task.drawingPagePath, task.defectInfor2RestorationDesk);
  381. }
  382. stopwatch.Stop();
  383. task.stopwatch[4] = stopwatch.ElapsedMilliseconds;
  384. liStep = 6;
  385. task.bmpCompress = yolo2.ResizesMat_4(task.bmp);
  386. task.isSucceed = true;
  387. callback(task);
  388. }
  389. else
  390. {
  391. task.isSucceed = true;
  392. callback(task);
  393. }
  394. }
  395. Thread.Sleep(5);
  396. }
  397. catch (Exception ex)
  398. {
  399. WarningEvent?.Invoke(WarningEnum.Low, $"DefectLib task3 err({liStep}):" + ex.Message);
  400. task.isSucceed = false;
  401. task.resultInfo = ex.Message;
  402. callback(task);
  403. }
  404. }
  405. }
  406. private void run4()
  407. {
  408. while (IsInit)
  409. {
  410. if (taskOperationList.Count < 1)
  411. {
  412. Thread.Sleep(5);
  413. continue;
  414. }
  415. //
  416. var task = pop2();
  417. int liStep = 0;
  418. try
  419. {
  420. if (task != null)
  421. {
  422. Stopwatch stopwatch = Stopwatch.StartNew();
  423. //====运行推理(必需单队列)
  424. stopwatch.Start();
  425. IDisposableReadOnlyCollection<DisposableNamedOnnxValue>[] results = yolo3.RunModlel(_onnxSession3, task.tensors);
  426. liStep = 1;
  427. task.informationList = yolo3.ScreeningResults_YD(results, task.bmps_resize, task.thresholds, task.thresholdsClass, task.recAreaThreshold);
  428. liStep = 2;
  429. //当前大图上缺陷个数
  430. int currPicDefectCount = 0;
  431. for (int x = 0; x < task.informationList.Count(); x++)
  432. currPicDefectCount += task.informationList[x].Count();
  433. task.defectCount = currPicDefectCount;
  434. stopwatch.Stop();
  435. task.stopwatch[3] = stopwatch.ElapsedMilliseconds;
  436. liStep = 3;
  437. if (task.informationList.Count > 0)
  438. {
  439. liStep = 4;
  440. //lock (taskTagList)
  441. // taskTagList.Add(task);
  442. //====打标 ,有缺陷返回缺陷图片数组,没缺陷返回所有图片数组
  443. stopwatch.Restart();
  444. task.bmps_tag = yolo3.DrawYoloPrediction2Mat(task.bmps_cut, task.informationList, 27, SixLabors.ImageSharp.Color.OrangeRed, task.resize.Width,
  445. task.Xmm, task.Ymm, out task.defectInfor2RestorationDesk);
  446. liStep = 5;
  447. if (ConfMgr.Instance.SysConfigParams.OpenFlawDistribution)
  448. {
  449. //大图缺陷坐标转换到图纸坐标
  450. if (!string.IsNullOrWhiteSpace(task.drawingPagePath) && task.defectInfor2RestorationDesk != null && task.defectInfor2RestorationDesk.Count > 0)
  451. task.defectInfor2RestorationDeskPage = yolo3.DefectDrawGerberImage(task.drawingPagePath, task.defectInfor2RestorationDesk);
  452. }
  453. stopwatch.Stop();
  454. task.stopwatch[4] = stopwatch.ElapsedMilliseconds;
  455. liStep = 6;
  456. task.bmpCompress = yolo3.ResizesMat_4(task.bmp);
  457. task.isSucceed = true;
  458. callback(task);
  459. }
  460. else
  461. {
  462. task.isSucceed = true;
  463. callback(task);
  464. }
  465. }
  466. Thread.Sleep(5);
  467. }
  468. catch (Exception ex)
  469. {
  470. WarningEvent?.Invoke(WarningEnum.Low, $"DefectLib task4 err({liStep}):" + ex.Message);
  471. task.isSucceed = false;
  472. task.resultInfo = ex.Message;
  473. callback(task);
  474. }
  475. }
  476. }
  477. /// <summary>
  478. /// 已不用
  479. /// </summary>
  480. private void run5()
  481. {
  482. while (IsInit)
  483. {
  484. if (taskTagList.Count < 1)
  485. {
  486. Thread.Sleep(0);
  487. continue;
  488. }
  489. //
  490. var task = pop3();
  491. try
  492. {
  493. if (task != null)
  494. {
  495. Stopwatch stopwatch = Stopwatch.StartNew();
  496. //====打标 ,有缺陷返回缺陷图片数组,没缺陷返回所有图片数组
  497. stopwatch.Start();
  498. task.bmps_tag = yolo1.DrawYoloPrediction2Mat(task.bmps_cut, task.informationList, 27, SixLabors.ImageSharp.Color.OrangeRed, task.resize.Width,
  499. task.Xmm,task.Ymm,out task.defectInfor2RestorationDesk);
  500. stopwatch.Stop();
  501. task.stopwatch[4] = stopwatch.ElapsedMilliseconds;
  502. task.isSucceed = true;
  503. callback(task);
  504. }
  505. }
  506. catch (Exception ex)
  507. {
  508. WarningEvent?.Invoke(WarningEnum.Low, "DefectLib task3 err:" + ex.Message);
  509. task.isSucceed = false;
  510. task.resultInfo = ex.Message;
  511. callback(task);
  512. }
  513. }
  514. }
  515. private void callback(DefectTask task)
  516. {
  517. //返回成功/失败,异步调用
  518. if (task.finishEvent != null || (task.finishEvent = finishEvent) != null)
  519. //task.finishEvent.BeginInvoke(result, errInfo, res => task.finishEvent.EndInvoke(res), null);
  520. System.Threading.ThreadPool.QueueUserWorkItem(waitCallback, task);
  521. }
  522. //异步回调
  523. WaitCallback waitCallback = new WaitCallback(o =>
  524. {
  525. var task = (DefectTask)o;
  526. task.finishEvent(task);
  527. });
  528. public class DefectTask
  529. {
  530. public int stepIndex;
  531. public string processName;
  532. public string drawingPagePath;//图纸路径bmp
  533. //图索引
  534. public int index = 0;
  535. /// <summary>
  536. /// 绝对位置-----X2轴
  537. /// </summary>
  538. public double Xmm;
  539. /// <summary>
  540. /// 绝对位置-----Y轴
  541. /// </summary>
  542. public double Ymm;
  543. /// <summary>
  544. /// 源文件
  545. /// </summary>
  546. public Mat bmp;
  547. public Mat bmpCompress;//压缩有缺陷大图
  548. public System.Drawing.Size cut_size = new System.Drawing.Size(592, 532);
  549. public System.Drawing.Size resize = new System.Drawing.Size(224, 224);
  550. /// <summary>
  551. /// 阈值
  552. /// </summary>
  553. public float thresholds = 0.4f;
  554. /// <summary>
  555. /// 种类阈值
  556. /// </summary>
  557. public string thresholdsClass;
  558. /// <summary>
  559. /// 缺陷在面积内数量
  560. /// </summary>
  561. public Dictionary<string, float> recAreaThreshold;
  562. /// <summary>
  563. /// 完成后回调
  564. /// </summary>
  565. public Action<DefectTask> finishEvent;
  566. //
  567. public long createTime = DateTime.Now.Ticks;
  568. public DateTime nowTime;
  569. //中间变量,供step2使用
  570. public Mat[] bmps_cut;
  571. public Mat[] bmps_resize;
  572. //预处理模型
  573. public Tensor<float>[] tensors;
  574. //==结果返回
  575. public List<Dictionary<int, List<string>[]>> informationList;
  576. public int defectCount;//informationList中的缺陷数
  577. public List<List<string>> defectInfor2RestorationDesk, defectInfor2RestorationDeskPage;//打标缺陷转为图纸的坐标
  578. public Bitmap[] bmps_tag; //打标小图 //bmps_tag.count<=bmps_cut.count bmps_tag.count=informationList.count
  579. public bool isSucceed;//转换是否成功
  580. public string resultInfo = "";//成功或失败信息
  581. public long[] stopwatch = new long[5];
  582. }
  583. public void add(DefectTask task)
  584. {
  585. lock (taskList)
  586. taskList.Add(task);
  587. }
  588. /// <summary>
  589. /// 打标 返回每张图的绝对位置X,Y
  590. /// </summary>
  591. /// <param name="defectBmpIndex">缺陷小图索引</param>
  592. /// <param name="X">拍照位绝对位置-----X2轴</param>
  593. /// <param name="Y">拍照位绝对位置-----Y轴</param>
  594. /// <param name="imagewidth">裁剪小图的宽592</param>
  595. /// <param name="imageheight">裁剪小图的高532</param>
  596. public List<double> makeTag(int defectBmpIndex, double X, double Y, int imagewidth, int imageheight)
  597. {
  598. return yolo1.ImageXY(defectBmpIndex, X, Y, imagewidth, imageheight);
  599. }
  600. /// <summary>
  601. /// 用相机1查看缺陷点
  602. /// </summary>
  603. /// <param name="defectBmpIndex"></param>
  604. /// <param name="X"></param>
  605. /// <param name="Y"></param>
  606. /// <param name="imagewidth"></param>
  607. /// <param name="imageheight"></param>
  608. /// <returns></returns>
  609. public List<double> viewTag(int defectBmpIndex, double X, double Y, int imagewidth, int imageheight)
  610. {
  611. return yolo1.ImageXY2(defectBmpIndex, X, Y, imagewidth, imageheight);
  612. }
  613. private DefectTask pop()
  614. {
  615. lock (taskList)
  616. {
  617. if (taskList.Count < 1)
  618. return null;
  619. //int index = 0;// taskList.FindIndex(p => { return p.isSync; });
  620. //if (index < 0) index = 0;
  621. var task = taskList[0];
  622. taskList.RemoveAt(0);
  623. return task;
  624. }
  625. }
  626. private DefectTask pop2()
  627. {
  628. lock (taskOperationList)
  629. {
  630. if (taskOperationList.Count < 1)
  631. return null;
  632. //int index = 0;// taskList.FindIndex(p => { return p.isSync; });
  633. //if (index < 0) index = 0;
  634. var task = taskOperationList[0];
  635. taskOperationList.RemoveAt(0);
  636. return task;
  637. }
  638. }
  639. private DefectTask pop3()
  640. {
  641. lock (taskTagList)
  642. {
  643. if (taskTagList.Count < 1)
  644. return null;
  645. //int index = 0;// taskList.FindIndex(p => { return p.isSync; });
  646. //if (index < 0) index = 0;
  647. var task = taskTagList[0];
  648. taskTagList.RemoveAt(0);
  649. return task;
  650. }
  651. }
  652. public void Dispose()
  653. {
  654. stop();
  655. }
  656. }
  657. }