Form_Home.cs 316 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490149114921493149414951496149714981499150015011502150315041505150615071508150915101511151215131514151515161517151815191520152115221523152415251526152715281529153015311532153315341535153615371538153915401541154215431544154515461547154815491550155115521553155415551556155715581559156015611562156315641565156615671568156915701571157215731574157515761577157815791580158115821583158415851586158715881589159015911592159315941595159615971598159916001601160216031604160516061607160816091610161116121613161416151616161716181619162016211622162316241625162616271628162916301631163216331634163516361637163816391640164116421643164416451646164716481649165016511652165316541655165616571658165916601661166216631664166516661667166816691670167116721673167416751676167716781679168016811682168316841685168616871688168916901691169216931694169516961697169816991700170117021703170417051706170717081709171017111712171317141715171617171718171917201721172217231724172517261727172817291730173117321733173417351736173717381739174017411742174317441745174617471748174917501751175217531754175517561757175817591760176117621763176417651766176717681769177017711772177317741775177617771778177917801781178217831784178517861787178817891790179117921793179417951796179717981799180018011802180318041805180618071808180918101811181218131814181518161817181818191820182118221823182418251826182718281829183018311832183318341835183618371838183918401841184218431844184518461847184818491850185118521853185418551856185718581859186018611862186318641865186618671868186918701871187218731874187518761877187818791880188118821883188418851886188718881889189018911892189318941895189618971898189919001901190219031904190519061907190819091910191119121913191419151916191719181919192019211922192319241925192619271928192919301931193219331934193519361937193819391940194119421943194419451946194719481949195019511952195319541955195619571958195919601961196219631964196519661967196819691970197119721973197419751976197719781979198019811982198319841985198619871988198919901991199219931994199519961997199819992000200120022003200420052006200720082009201020112012201320142015201620172018201920202021202220232024202520262027202820292030203120322033203420352036203720382039204020412042204320442045204620472048204920502051205220532054205520562057205820592060206120622063206420652066206720682069207020712072207320742075207620772078207920802081208220832084208520862087208820892090209120922093209420952096209720982099210021012102210321042105210621072108210921102111211221132114211521162117211821192120212121222123212421252126212721282129213021312132213321342135213621372138213921402141214221432144214521462147214821492150215121522153215421552156215721582159216021612162216321642165216621672168216921702171217221732174217521762177217821792180218121822183218421852186218721882189219021912192219321942195219621972198219922002201220222032204220522062207220822092210221122122213221422152216221722182219222022212222222322242225222622272228222922302231223222332234223522362237223822392240224122422243224422452246224722482249225022512252225322542255225622572258225922602261226222632264226522662267226822692270227122722273227422752276227722782279228022812282228322842285228622872288228922902291229222932294229522962297229822992300230123022303230423052306230723082309231023112312231323142315231623172318231923202321232223232324232523262327232823292330233123322333233423352336233723382339234023412342234323442345234623472348234923502351235223532354235523562357235823592360236123622363236423652366236723682369237023712372237323742375237623772378237923802381238223832384238523862387238823892390239123922393239423952396239723982399240024012402240324042405240624072408240924102411241224132414241524162417241824192420242124222423242424252426242724282429243024312432243324342435243624372438243924402441244224432444244524462447244824492450245124522453245424552456245724582459246024612462246324642465246624672468246924702471247224732474247524762477247824792480248124822483248424852486248724882489249024912492249324942495249624972498249925002501250225032504250525062507250825092510251125122513251425152516251725182519252025212522252325242525252625272528252925302531253225332534253525362537253825392540254125422543254425452546254725482549255025512552255325542555255625572558255925602561256225632564256525662567256825692570257125722573257425752576257725782579258025812582258325842585258625872588258925902591259225932594259525962597259825992600260126022603260426052606260726082609261026112612261326142615261626172618261926202621262226232624262526262627262826292630263126322633263426352636263726382639264026412642264326442645264626472648264926502651265226532654265526562657265826592660266126622663266426652666266726682669267026712672267326742675267626772678267926802681268226832684268526862687268826892690269126922693269426952696269726982699270027012702270327042705270627072708270927102711271227132714271527162717271827192720272127222723272427252726272727282729273027312732273327342735273627372738273927402741274227432744274527462747274827492750275127522753275427552756275727582759276027612762276327642765276627672768276927702771277227732774277527762777277827792780278127822783278427852786278727882789279027912792279327942795279627972798279928002801280228032804280528062807280828092810281128122813281428152816281728182819282028212822282328242825282628272828282928302831283228332834283528362837283828392840284128422843284428452846284728482849285028512852285328542855285628572858285928602861286228632864286528662867286828692870287128722873287428752876287728782879288028812882288328842885288628872888288928902891289228932894289528962897289828992900290129022903290429052906290729082909291029112912291329142915291629172918291929202921292229232924292529262927292829292930293129322933293429352936293729382939294029412942294329442945294629472948294929502951295229532954295529562957295829592960296129622963296429652966296729682969297029712972297329742975297629772978297929802981298229832984298529862987298829892990299129922993299429952996299729982999300030013002300330043005300630073008300930103011301230133014301530163017301830193020302130223023302430253026302730283029303030313032303330343035303630373038303930403041304230433044304530463047304830493050305130523053305430553056305730583059306030613062306330643065306630673068306930703071307230733074307530763077307830793080308130823083308430853086308730883089309030913092309330943095309630973098309931003101310231033104310531063107310831093110311131123113311431153116311731183119312031213122312331243125312631273128312931303131313231333134313531363137313831393140314131423143314431453146314731483149315031513152315331543155315631573158315931603161316231633164316531663167316831693170317131723173317431753176317731783179318031813182318331843185318631873188318931903191319231933194319531963197319831993200320132023203320432053206320732083209321032113212321332143215321632173218321932203221322232233224322532263227322832293230323132323233323432353236323732383239324032413242324332443245324632473248324932503251325232533254325532563257325832593260326132623263326432653266326732683269327032713272327332743275327632773278327932803281328232833284328532863287328832893290329132923293329432953296329732983299330033013302330333043305330633073308330933103311331233133314331533163317331833193320332133223323332433253326332733283329333033313332333333343335333633373338333933403341334233433344334533463347334833493350335133523353335433553356335733583359336033613362336333643365336633673368336933703371337233733374337533763377337833793380338133823383338433853386338733883389339033913392339333943395339633973398339934003401340234033404340534063407340834093410341134123413341434153416341734183419342034213422342334243425342634273428342934303431343234333434343534363437343834393440344134423443344434453446344734483449345034513452345334543455345634573458345934603461346234633464346534663467346834693470347134723473347434753476347734783479348034813482348334843485348634873488348934903491349234933494349534963497349834993500350135023503350435053506350735083509351035113512351335143515351635173518351935203521352235233524352535263527352835293530353135323533353435353536353735383539354035413542354335443545354635473548354935503551355235533554355535563557355835593560356135623563356435653566356735683569357035713572357335743575357635773578357935803581358235833584358535863587358835893590359135923593359435953596359735983599360036013602360336043605360636073608360936103611361236133614361536163617361836193620362136223623362436253626362736283629363036313632363336343635363636373638363936403641364236433644364536463647364836493650365136523653365436553656365736583659366036613662366336643665366636673668366936703671367236733674367536763677367836793680368136823683368436853686368736883689369036913692369336943695369636973698369937003701370237033704370537063707370837093710371137123713371437153716371737183719372037213722372337243725372637273728372937303731373237333734373537363737373837393740374137423743374437453746374737483749375037513752375337543755375637573758375937603761376237633764376537663767376837693770377137723773377437753776377737783779378037813782378337843785378637873788378937903791379237933794379537963797379837993800380138023803380438053806380738083809381038113812381338143815381638173818381938203821382238233824382538263827382838293830383138323833383438353836383738383839384038413842384338443845384638473848384938503851385238533854385538563857385838593860386138623863386438653866386738683869387038713872387338743875387638773878387938803881388238833884388538863887388838893890389138923893389438953896389738983899390039013902390339043905390639073908390939103911391239133914391539163917391839193920392139223923392439253926392739283929393039313932393339343935393639373938393939403941394239433944394539463947394839493950395139523953395439553956395739583959396039613962396339643965396639673968396939703971397239733974397539763977397839793980398139823983398439853986398739883989399039913992399339943995399639973998399940004001400240034004400540064007400840094010401140124013401440154016401740184019402040214022402340244025402640274028402940304031403240334034403540364037403840394040404140424043404440454046404740484049405040514052405340544055405640574058405940604061406240634064406540664067406840694070407140724073407440754076407740784079408040814082408340844085408640874088408940904091409240934094409540964097409840994100410141024103410441054106410741084109411041114112411341144115411641174118411941204121412241234124412541264127412841294130413141324133413441354136413741384139414041414142414341444145414641474148414941504151415241534154415541564157415841594160416141624163416441654166416741684169417041714172417341744175417641774178417941804181418241834184418541864187418841894190419141924193419441954196419741984199420042014202420342044205420642074208420942104211421242134214421542164217421842194220422142224223422442254226422742284229423042314232423342344235423642374238423942404241424242434244424542464247424842494250425142524253425442554256425742584259426042614262426342644265426642674268426942704271427242734274427542764277427842794280428142824283428442854286428742884289429042914292429342944295429642974298429943004301430243034304430543064307430843094310431143124313431443154316431743184319432043214322432343244325432643274328432943304331433243334334433543364337433843394340434143424343434443454346434743484349435043514352435343544355435643574358435943604361436243634364436543664367436843694370437143724373437443754376437743784379438043814382438343844385438643874388438943904391439243934394439543964397439843994400440144024403440444054406440744084409441044114412441344144415441644174418441944204421442244234424442544264427442844294430443144324433443444354436443744384439444044414442444344444445444644474448444944504451445244534454445544564457445844594460446144624463446444654466446744684469447044714472447344744475447644774478447944804481448244834484448544864487448844894490449144924493449444954496449744984499450045014502450345044505450645074508450945104511451245134514451545164517451845194520452145224523452445254526452745284529453045314532453345344535453645374538453945404541454245434544454545464547454845494550455145524553455445554556455745584559456045614562456345644565456645674568456945704571457245734574457545764577457845794580458145824583458445854586458745884589459045914592459345944595459645974598459946004601460246034604460546064607460846094610461146124613461446154616461746184619462046214622462346244625462646274628462946304631463246334634463546364637463846394640464146424643464446454646464746484649465046514652465346544655465646574658465946604661466246634664466546664667466846694670467146724673467446754676467746784679468046814682468346844685468646874688468946904691469246934694469546964697469846994700470147024703470447054706470747084709471047114712471347144715471647174718471947204721472247234724472547264727472847294730473147324733473447354736473747384739474047414742474347444745474647474748474947504751475247534754475547564757475847594760476147624763476447654766476747684769477047714772477347744775477647774778477947804781478247834784478547864787478847894790479147924793479447954796479747984799480048014802480348044805480648074808480948104811481248134814481548164817481848194820482148224823482448254826482748284829483048314832483348344835483648374838483948404841484248434844484548464847484848494850485148524853485448554856485748584859486048614862486348644865486648674868486948704871487248734874487548764877487848794880488148824883488448854886488748884889489048914892489348944895489648974898489949004901490249034904490549064907490849094910491149124913491449154916491749184919492049214922492349244925492649274928492949304931493249334934493549364937493849394940494149424943494449454946494749484949495049514952495349544955495649574958495949604961496249634964496549664967496849694970497149724973497449754976497749784979498049814982498349844985498649874988498949904991499249934994499549964997499849995000500150025003500450055006500750085009501050115012501350145015501650175018501950205021502250235024502550265027502850295030503150325033503450355036503750385039504050415042504350445045504650475048504950505051505250535054505550565057505850595060506150625063506450655066506750685069507050715072507350745075507650775078507950805081508250835084508550865087508850895090509150925093509450955096509750985099510051015102510351045105510651075108510951105111511251135114511551165117511851195120512151225123512451255126512751285129513051315132513351345135513651375138513951405141514251435144514551465147514851495150515151525153515451555156515751585159516051615162516351645165516651675168516951705171517251735174517551765177517851795180518151825183518451855186518751885189519051915192519351945195519651975198519952005201520252035204520552065207520852095210521152125213521452155216521752185219522052215222522352245225522652275228522952305231523252335234523552365237523852395240524152425243524452455246524752485249525052515252525352545255525652575258525952605261526252635264526552665267526852695270527152725273527452755276527752785279528052815282528352845285528652875288528952905291529252935294529552965297529852995300530153025303530453055306530753085309531053115312531353145315531653175318531953205321532253235324532553265327532853295330533153325333533453355336533753385339534053415342534353445345534653475348534953505351535253535354535553565357535853595360536153625363536453655366536753685369537053715372537353745375537653775378537953805381538253835384538553865387538853895390539153925393539453955396539753985399540054015402540354045405540654075408540954105411541254135414541554165417541854195420542154225423542454255426542754285429543054315432543354345435543654375438543954405441544254435444544554465447544854495450545154525453545454555456545754585459546054615462546354645465546654675468546954705471547254735474547554765477547854795480548154825483548454855486548754885489549054915492549354945495549654975498549955005501550255035504550555065507550855095510551155125513551455155516551755185519552055215522552355245525552655275528552955305531553255335534553555365537553855395540554155425543554455455546554755485549555055515552555355545555555655575558555955605561556255635564556555665567556855695570557155725573557455755576557755785579558055815582558355845585558655875588558955905591559255935594559555965597559855995600560156025603560456055606560756085609561056115612561356145615561656175618561956205621562256235624562556265627562856295630563156325633563456355636563756385639564056415642564356445645564656475648564956505651565256535654565556565657565856595660566156625663566456655666566756685669567056715672567356745675567656775678567956805681568256835684568556865687568856895690569156925693569456955696569756985699570057015702570357045705570657075708570957105711571257135714571557165717571857195720572157225723572457255726572757285729573057315732573357345735573657375738573957405741574257435744574557465747574857495750575157525753575457555756575757585759576057615762576357645765576657675768576957705771577257735774577557765777577857795780578157825783578457855786578757885789579057915792579357945795579657975798579958005801580258035804580558065807580858095810581158125813581458155816581758185819582058215822582358245825582658275828582958305831583258335834583558365837583858395840584158425843584458455846584758485849585058515852585358545855585658575858585958605861586258635864586558665867586858695870587158725873587458755876587758785879588058815882588358845885588658875888588958905891589258935894589558965897589858995900590159025903590459055906590759085909591059115912
  1. using Newtonsoft.Json;
  2. using System;
  3. using System.Collections.Generic;
  4. using System.Data;
  5. using System.IO;
  6. using System.Linq;
  7. using System.Text;
  8. using Microsoft.Win32;
  9. using System.Threading;
  10. using System.Threading.Tasks;
  11. using System.Windows.Forms;
  12. using HslCommunication.LogNet;
  13. using MainForm.FaForm;
  14. using NPOI.Util;
  15. using Sunny.UI;
  16. using MainForm.ClassFile.XiaomiAPI;
  17. using System.Diagnostics;
  18. using MainForm.Models;
  19. using SqlSugar;
  20. using EasyModbus;
  21. using ModBusClientSimple.Util;
  22. using MainForm.ClassFile.XiaomiAPI_MES;
  23. using static MainForm.ClassFile.XiaomiAPI.XiaomiMqttClient_Extend;
  24. using static MainForm.ClassFile.XiaomiAPI_MES.XiaomiMESHttp_StationOutbound;
  25. using static MainForm.ClassFile.XiaomiAPI_MES.XiaomiMESHttp_StationInbound;
  26. using EIP_Protocol;
  27. using DevComponents.DotNetBar.Controls;
  28. using ICSharpCode.SharpZipLib.Zip;
  29. using static MainForm.SQLHelper;
  30. /*
  31. * 注:本源码对外提供,所以有些地方使用中文命名方法及变量
  32. */
  33. namespace MainForm
  34. {
  35. /// <summary>
  36. /// 记录日志的委托
  37. /// </summary>
  38. /// <param name="logType">日志类型</param>
  39. /// <param name="message">日志信息</param>
  40. public delegate void HomeMessageHandler(LogType logType, string message);
  41. /// <summary>
  42. /// 主页窗体
  43. /// </summary>
  44. public partial class Form_Home : Form
  45. {
  46. #region 常量
  47. //文本常量
  48. private const string Head = "开始采集";
  49. private const string Tail = "采集完成";
  50. private const string Body = "工位出站数据";
  51. private const string BodyCheck = "工位点检数据";
  52. private const string BodyRun = "整线运行数据";
  53. private const string BodyAlarm = "整线报警数据";
  54. #endregion 常量
  55. #region 变量
  56. /// <summary>
  57. /// 委托-记录日志的方法
  58. /// </summary>
  59. public event HomeMessageHandler MessageEvent;
  60. /// <summary>
  61. /// 日志接口
  62. /// </summary>
  63. ILogNet _PLCLogNet;
  64. /// <summary>
  65. /// 用于记录MQTT日志
  66. /// </summary>
  67. ILogNet _MqttLogNet;
  68. //private int DataSwitch = 1; // 1-SQLServer;2-Excel
  69. // 定义信号量,index0给MES(true有信号,false无信号;set()让被控线程运行,Reset()让被控线程停止;WaitOne(等待时间)等待线程运行)
  70. //间隔时间
  71. private int IntervalReadPLC = 300; //ms 读PLC
  72. private int IntervalMonitorMES = 1000; //ms MES心跳
  73. private int IntervalUpHead = 1000; //ms 上位机心跳(给PLC用)
  74. private int IntervalAlarm = 1000; //ms 数据(报警)查询与设备运行信息
  75. //定义一个字典,存plc对象(通讯)
  76. //ModbusClientHelper plc1Alarm; // PLC‘运行数据’与‘报警数据’线程用ModbusTCP
  77. //Dictionary<int, ModbusClientHelper> Funs = new Dictionary<int, ModbusClientHelper>();
  78. Inovance_EIP plc1Alarm; // PLC‘运行数据’与‘报警数据’线程用ModbusTCP
  79. Dictionary<int, Inovance_EIP> Funs = new Dictionary<int, Inovance_EIP>();
  80. /// <summary>
  81. /// 上次的设备运行信息
  82. /// </summary>
  83. private string lineWorkingData1_OldStr = string.Empty;
  84. /// <summary>
  85. /// 设备报警字典-当前结果
  86. /// Dictionary<工位代码,List<报警信息>>
  87. /// </summary>
  88. private Dictionary<string, List<Alarm>> DicAlarms_Cur = new Dictionary<string, List<Alarm>>();
  89. #endregion 变量
  90. #region 窗体基础事件
  91. /// <summary>
  92. /// 初始化
  93. /// </summary>
  94. public Form_Home()
  95. {
  96. InitializeComponent();
  97. CheckForIllegalCrossThreadCalls = false; // 不检查跨线程访问
  98. _PLCLogNet = new LogNetDateTime(GlobalContext.PlcLogDir, GenerateMode.ByEveryDay); // 按天记录日志
  99. _MqttLogNet = new LogNetDateTime(GlobalContext.MqttLogDir, GenerateMode.ByEveryHour); // 按小时记录日志
  100. GlobalContext.Set += new Action(UpdateProductInfo); // 产品信息变化时更新UI
  101. }
  102. /// <summary>
  103. /// 窗体加载事件
  104. /// </summary>
  105. private void Form_Home_Load(object sender, EventArgs e)
  106. {
  107. try
  108. {
  109. AddMessage(LogType.Info, "开始初始化程序");
  110. InitalDicAlarm(); // 实例化报警字典
  111. //组建plc对象字典
  112. //plc1Alarm = new ModbusClientHelper(GlobalContext.Machine1Address, GlobalContext.MachinePort);
  113. //plc1Alarm = new Inovance_EIP(GlobalContext.PCAddress, GlobalContext.Machine1Address);
  114. if (GlobalContext.IsUsePLC1)
  115. Funs.Add(1, new Inovance_EIP(GlobalContext.PCAddress, GlobalContext.Machine1Address)); //OP10 壳体清洁上料装备
  116. //Funs.Add(1, new ModbusClientHelper(GlobalContext.Machine1Address, GlobalContext.MachinePort, 2001)); // Tray盘上料装备(板测)
  117. if (GlobalContext.IsUsePLC2)
  118. //Funs.Add(2, new ModbusClientHelper(GlobalContext.Machine2Address, GlobalContext.MachinePort, 2001)); // FCT(板测),
  119. Funs.Add(2, new Inovance_EIP(GlobalContext.PCAddress, GlobalContext.Machine2Address)); //OP20 顶盖上料设备
  120. if (GlobalContext.IsUsePLC3)
  121. Funs.Add(3, new Inovance_EIP(GlobalContext.PCAddress, GlobalContext.Machine3Address)); //OP30 点胶设备
  122. //Funs.Add(3, new ModbusClientHelper(GlobalContext.Machine3Address, GlobalContext.MachinePort, 2001)); // 值板机,
  123. if (GlobalContext.IsUsePLC4)
  124. Funs.Add(4, new Inovance_EIP(GlobalContext.PCAddress, GlobalContext.Machine4Address)); //OP40 3D胶线检测
  125. //Funs.Add(4, new ModbusClientHelper(GlobalContext.Machine4Address, GlobalContext.MachinePort, 2001)); // 取放桁
  126. if (GlobalContext.IsUsePLC5)
  127. Funs.Add(5, new Inovance_EIP(GlobalContext.PCAddress, GlobalContext.Machine5Address)); //OP50 ADD PCB板上料
  128. //Funs.Add(5, new ModbusClientHelper(GlobalContext.Machine5Address, GlobalContext.MachinePort, 2001)); //Tray盘下料装备
  129. if (GlobalContext.IsUsePLC6)
  130. Funs.Add(6, new Inovance_EIP(GlobalContext.PCAddress, GlobalContext.Machine6Address)); //OP60 顶盖装配
  131. if (GlobalContext.IsUsePLC7)
  132. Funs.Add(7, new Inovance_EIP(GlobalContext.PCAddress, GlobalContext.Machine7Address)); //OP70 锁螺丝
  133. if (GlobalContext.IsUsePLC8)
  134. Funs.Add(8, new Inovance_EIP(GlobalContext.PCAddress, GlobalContext.Machine8Address)); //OP80 3D螺丝高度检测,NG出料站
  135. if (GlobalContext.IsUsePLC9)
  136. Funs.Add(9, new Inovance_EIP(GlobalContext.PCAddress, GlobalContext.Machine9Address)); //OP90 下料站
  137. foreach (Inovance_EIP plcEIP in Funs.Values)
  138. {
  139. if (plcEIP != null)
  140. {
  141. try
  142. {
  143. plcEIP.Connect();
  144. }
  145. catch (Exception ex)
  146. {
  147. MessageBox.Show($"PLC[{GlobalContext.Machine1Address}]连接失败!失败信息:" + ex.Message,
  148. "PLC连接提示", MessageBoxButtons.OK, MessageBoxIcon.Error, MessageBoxDefaultButton.Button1, MessageBoxOptions.ServiceNotification);
  149. }
  150. }
  151. }
  152. /*
  153. //plc1Alarm.Connect();
  154. foreach (ModbusClientHelper modbusClient in Funs.Values)
  155. {
  156. if (modbusClient != null)
  157. {
  158. try
  159. {
  160. modbusClient.Connect();
  161. }
  162. catch (Exception ex)
  163. {
  164. MessageBox.Show($"PLC[{modbusClient.IPAddress}:{modbusClient.Port}]连接失败!失败信息:" + ex.Message,
  165. "PLC连接提示", MessageBoxButtons.OK, MessageBoxIcon.Error, MessageBoxDefaultButton.Button1, MessageBoxOptions.ServiceNotification);
  166. }
  167. }
  168. }
  169. */
  170. // 采集任务
  171. Task TaskReadAlarm = new Task(ReadAlarmAllPLC); // 线程-获取线体报警数据
  172. List<Task> TaskReadProcess = new List<Task>(); // 线程-触发点位(PLC)的线程
  173. //TaskReadProcess.Add(new Task(() => { ReadStation_DownOrderInfo(1); })); // 下发机种
  174. if (GlobalContext.IsUsePLC1)
  175. TaskReadProcess.Add(new Task(() => { ReadStation_S1(1); })); //OP10 壳体清洁上料装备
  176. if (GlobalContext.IsUsePLC2)
  177. TaskReadProcess.Add(new Task(() => { ReadStation_S2(2); })); //OP20 顶盖上料设备
  178. if (GlobalContext.IsUsePLC3)
  179. TaskReadProcess.Add(new Task(() => { ReadStation_S3(3); })); //OP30 点胶设备
  180. if (GlobalContext.IsUsePLC4)
  181. TaskReadProcess.Add(new Task(() => { ReadStation_S4(4); })); //OP40 点胶检测设备
  182. if (GlobalContext.IsUsePLC5)
  183. TaskReadProcess.Add(new Task(() => { ReadStation_S5(5); })); //OP50 ADD PCB板上料设备
  184. /*
  185. if (GlobalContext.IsUsePLC6)
  186. TaskReadProcess.Add(new Task(() => { ReadStation_S6(6); })); //OP60 顶盖装配设备
  187. if (GlobalContext.IsUsePLC7)
  188. TaskReadProcess.Add(new Task(() => { ReadStation_S7(7); })); //OP70 锁螺丝设备
  189. if (GlobalContext.IsUsePLC8)
  190. TaskReadProcess.Add(new Task(() => { ReadStation_S8(8); })); //OP80 3D螺丝高度检测设备
  191. if (GlobalContext.IsUsePLC9)
  192. TaskReadProcess.Add(new Task(() => { ReadStation_S9(9); })); //OP90 下料设备
  193. */
  194. #region 初始化
  195. try
  196. {
  197. // 开启MES(Http)
  198. //bool mesret = HttpUitls.PingIP(GlobalContext.ServerHost1);
  199. //if (mesret)
  200. //{
  201. // OnMessage(LogType.Info, "MES初始连接正常");
  202. // pictureBoxMESStatus.Image = imageListState.Images[1];
  203. // GlobalContext.MESIsConnect = true;
  204. //}
  205. //else
  206. //{
  207. // OnMessage(LogType.Info, "MES初始连接失败");
  208. // pictureBoxMESStatus.Image = imageListState.Images[0];
  209. // GlobalContext.MESIsConnect = false;
  210. //}
  211. // 开启IOT(MQTT)
  212. string addr = GlobalContext.MQTTServerHost;
  213. int port = GlobalContext.MQTTServerPort;
  214. int qmttResult = XiaomiMqttClient_Extend.OpenWithMqttServer(addr, port, GlobalContext.MqttServerPath, GlobalContext.MqttServerName);
  215. XiaomiMqttResponse_ErrCode response_ErrCode = (XiaomiMqttResponse_ErrCode)qmttResult;
  216. if (response_ErrCode == XiaomiMqttResponse_ErrCode.OK)
  217. {
  218. AddMessage(LogType.Info, "小米MQTT连接成功!--- OK");
  219. pictureBoxMESStatus.Image = imageListState.Images[1];
  220. GlobalContext.IOTIsConnect1 = true;
  221. XiaomiMqttClient_Extend.SetCallbackWithDataId(CallbackWithDataId);
  222. }
  223. else
  224. {
  225. AddMessage(LogType.Info, $"小米MQTT连接失败!--- {response_ErrCode.ToString()}");
  226. pictureBoxMESStatus.Image = imageListState.Images[0];
  227. GlobalContext.IOTIsConnect1 = false;
  228. }
  229. // 开启AGV HTTP
  230. //bool mesret = HttpUitls.PingIP(GlobalContext.ServerHost1);
  231. //if (mesret)
  232. //{
  233. // OnMessage(LogType.Info, "MES初始连接正常");
  234. // pictureBoxMESStatus.Image = imageListState.Images[1];
  235. // GlobalContext.MESIsConnect = true;
  236. //}
  237. //else
  238. //{
  239. // OnMessage(LogType.Info, "MES初始连接失败");
  240. // pictureBoxMESStatus.Image = imageListState.Images[0];
  241. // GlobalContext.MESIsConnect = false;
  242. //}
  243. // 开启AGV MQTT
  244. // 持续监视MES、IOT、AGV HTTP、AGV MQTT连接状态
  245. Task.Run(MonitorMESConnect);
  246. // 查询PLC连接状态
  247. foreach (int plcNo in Funs.Keys)
  248. {
  249. bool connected = Funs[plcNo].IsConnected;
  250. if (connected)
  251. {
  252. string msg = plcNo.ToString() + "工位初始连接成功---" + Funs[plcNo]._plcIPStr;
  253. AddMessage(LogType.Info, msg);
  254. UpdatePLCMonitor(1, plcNo, 1); // 更新PLC状态的UI
  255. }
  256. else
  257. {
  258. string msg = plcNo.ToString() + "工位初始连接失败---" + Funs[plcNo]._plcIPStr;
  259. AddMessage(LogType.Info, msg);
  260. UpdatePLCMonitor(1, plcNo, 0); // 更新PLC状态的UI
  261. }
  262. }
  263. // 开启PLC的业务处理线程-监听PLC点位+状态
  264. foreach (Task task in TaskReadProcess)
  265. {
  266. if (task != null)
  267. task.Start();
  268. }
  269. //// 开启“获取线体报警数据”的线程
  270. //TaskReadAlarm.Start();
  271. ////下传MES信息给1工位(先判断下plc对象数量)
  272. //if (Funs.Count > 1)
  273. // DownLoadProductInfo(1);
  274. AddMessage(LogType.Info, "程序初始化完成");
  275. }
  276. catch (Exception ex)
  277. {
  278. string str = ex.StackTrace;
  279. this.BeginInvoke(new Action(() =>
  280. {
  281. AddMessage(LogType.Error, "初始化PLC连接失败!异常信息:" + ex.Message + ";异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  282. }));
  283. }
  284. #endregion
  285. }
  286. catch (Exception ex)
  287. {
  288. string str = ex.StackTrace;
  289. OnMessage(LogType.Info, "主窗体的首页初始化出错!异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1) + ";异常信息:" + ex.Message.ToString());
  290. if (ex.Message != null && ex.Message.Contains("timed out"))
  291. MessageBox.Show("主窗体的首页初始化出错!异常信息:PLC连接超时!" + ex.Message);
  292. else
  293. MessageBox.Show("主窗体的首页初始化出错!异常信息:" + ex.Message);
  294. }
  295. }
  296. /// <summary>
  297. /// 窗体关闭事件
  298. /// </summary>
  299. private void Form_Home_FormClosed(object sender, FormClosedEventArgs e)
  300. {
  301. Closed2();
  302. }
  303. public void Closed2()
  304. {
  305. try
  306. {
  307. XiaomiMqttClient_Extend.CloseWithMqttServer(GlobalContext.MqttServerPath, GlobalContext.MqttServerName);
  308. }
  309. catch { }
  310. }
  311. #endregion 窗体基础事件
  312. #region 监控MES状态
  313. /// <summary>
  314. /// 监控MES连接状态
  315. /// </summary>
  316. private void MonitorMESConnect()
  317. {
  318. while (true) // 运行被控线程
  319. {
  320. bool mesret = XiaomiMqttClient.IsOpen;
  321. if (mesret)
  322. {
  323. pictureBoxMESStatus.Image = imageListState.Images[1];
  324. GlobalContext.IOTIsConnect1 = true;
  325. }
  326. else
  327. {
  328. OnMessage(LogType.Info, "MES1连接失败");
  329. pictureBoxMESStatus.Image = imageListState.Images[0];
  330. GlobalContext.IOTIsConnect1 = false;
  331. }
  332. Thread.Sleep(IntervalMonitorMES);
  333. }
  334. }
  335. #endregion 监控MES连接状态
  336. #region 采集设备状态、运行数据、报警数据
  337. /// <summary>
  338. /// 请求设备状态 5000
  339. /// </summary>
  340. /// <param name="no">1</param>
  341. /// <param name="stationNameStr"></param>
  342. /// <returns>0:证明未连接到PLC;1,代表设备控制状态处于运行状态;2,代表设备控制状态处于故障状态;3,代表设备控制状态处于缺料状态;4,代表设备控制状态处于待机状态;5,代表设备控制状态处于维修状态;</returns>
  343. public int GetDeviceStatus(int plcNo, string stationNameStr = "[S0]壳体上料")
  344. {
  345. try
  346. {
  347. if (Funs[plcNo].IsConnected) // 检查PLC是否已连接上
  348. {
  349. short result = 0; //Funs[plcNo].ReadHoldingRegisters<short>(5000); // 5000
  350. return result;
  351. }
  352. else
  353. {
  354. return 0;
  355. }
  356. }
  357. catch (Exception ex)
  358. {
  359. string str = ex.StackTrace;
  360. AddMessage_Station(stationNameStr, LogType.Error, "请求设备状态失败!" + ex.Message.ToString() + ";异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  361. return 0;
  362. }
  363. }
  364. /// <summary>
  365. /// 检查是否可采集点检数据 - 不取新值
  366. /// 5000不为1时可点检
  367. /// </summary>
  368. /// <returns></returns>
  369. public bool CheckCanSpotcheck1(int deviceState)
  370. {
  371. //return true;
  372. //D5000 = 1,代表设备控制状态处于运行状态
  373. //D5000 = 2, 代表设备控制状态处于故障状态
  374. //D5000 = 3,代表设备控制状态处于缺料状态
  375. //D5000 = 4, 代表设备控制状态处于待机状态
  376. //D5000 = 5,代表设备控制状态处于维修状态
  377. return deviceState != 1;
  378. }
  379. /// <summary>
  380. /// 检查是否可采集产品数据 - 不取新值
  381. /// </summary>
  382. /// <returns></returns>
  383. public bool CheckCanCollData(int deviceState)
  384. {
  385. return deviceState == 0; // 点检时该值不为0
  386. }
  387. /// <summary>
  388. /// 获取设备报警数据与获取设备运行信息
  389. /// </summary>
  390. private async void ReadAlarmAllPLC()
  391. {
  392. // [S1] Tray盘上料装备(板测)
  393. // [S2] FCT(板测)
  394. // [S3] 值板机
  395. // [S4] 取放桁架
  396. // [S5] Tray盘下料装备
  397. /// 上位机心跳
  398. /// 获取设备报警数据与状态信息
  399. string stationNameStr = "获取设备报警数据与状态信息";
  400. while (true)
  401. {
  402. try
  403. {
  404. if (!GlobalContext._IsCon_plc1Alarm)
  405. {
  406. UpdatePLCMonitor(1, -2, 0);
  407. continue;
  408. }
  409. if (plc1Alarm.IsConnected) // 检查PLC是否已连接上
  410. {
  411. DateTime dtNow = DateTime.Now;
  412. #region 获取设备运行信息
  413. try
  414. {
  415. LineWorkingData_ThisTime lineWorkingData1 = new LineWorkingData_ThisTime();
  416. lineWorkingData1.GUID = Guid.NewGuid().ToString();
  417. lineWorkingData1.LineName = GlobalContext.LineCode;
  418. //
  419. /*
  420. lineWorkingData1.BootTimeLong = plc1Alarm.ReadHoldingRegisters<float>(5500); // 本次开机时间(整线)D5500 h
  421. lineWorkingData1.NormalTimeLong = plc1Alarm.ReadHoldingRegisters<float>(5502); // 本次开机运行时间(整线)D5502 h
  422. lineWorkingData1.StandbyTimeLong = plc1Alarm.ReadHoldingRegisters<float>(5504); // 本次开机待机时间(整线)D5504 h
  423. lineWorkingData1.FaultTimeLong = plc1Alarm.ReadHoldingRegisters<float>(5506); // 本次开机故障时间(整线)D5506 h
  424. lineWorkingData1.MaterialShortageTimeLong = plc1Alarm.ReadHoldingRegisters<float>(5508); // 本次开机缺料时间(整线)D5508 h
  425. lineWorkingData1.MaintenanceTimeLong = plc1Alarm.ReadHoldingRegisters<float>(5510); // 本次开机维修时间(整线)D5510 h
  426. lineWorkingData1.FaultNumber = plc1Alarm.ReadHoldingRegisters<short>(5514); // 本次开机故障停机次数(整线)D5514
  427. lineWorkingData1.OutputNumber = plc1Alarm.ReadHoldingRegisters<short>(5700); // 本次开机产量(整线) D5700
  428. lineWorkingData1.QualifiedNumber = plc1Alarm.ReadHoldingRegisters<short>(5704); // 本次开机合格数量(整线) D5704
  429. lineWorkingData1.QualifiedRate = plc1Alarm.ReadHoldingRegisters<float>(5710); // 本次开机合格率(整线) D5710
  430. lineWorkingData1.DesignRhythm = plc1Alarm.ReadHoldingRegisters<float>(5714); // 设计节拍(整线) D5714
  431. lineWorkingData1.RealityRhythm = plc1Alarm.ReadHoldingRegisters<float>(5716); // 本次开机实际节拍(整线) D5716
  432. */
  433. lineWorkingData1.CreateTime = DateTime.Now;
  434. string lineWorkingData1_Str = JsonConvert.SerializeObject(lineWorkingData1);
  435. // UI展示-展示到设备状态页
  436. if (string.IsNullOrEmpty(lineWorkingData1_OldStr)) // 软件启动后第一次运行
  437. {
  438. // 查询数据库最新一条数据,确定是不是更新
  439. string qSql = @"SELECT top(1) [GUID]
  440. ,[LineName]
  441. ,[BootTimeLong]
  442. ,[NormalTimeLong]
  443. ,[StandbyTimeLong]
  444. ,[FaultTimeLong]
  445. ,[MaterialShortageTimeLong]
  446. ,[MaintenanceTimeLong]
  447. ,[FaultNumber]
  448. ,[OutputNumber]
  449. ,[QualifiedNumber]
  450. ,[QualifiedRate]
  451. ,[DesignRhythm]
  452. ,[RealityRhythm]
  453. ,[CreateTime]
  454. FROM [LineWorkingData]
  455. where [CreateTime] > '{0}'
  456. and [LineName]='{1}'
  457. order by [CreateTime] desc
  458. ";
  459. qSql = string.Format(qSql, DateTime.Now.ToString("yyyy-MM-dd") + " 00:00:00", lineWorkingData1.LineName);
  460. var ds = SQLHelper_New.Query(qSql, null);
  461. if (ds != null && ds.Tables.Count > 0 && ds.Tables[0].Rows.Count > 0)
  462. {
  463. var dataDBlast = new LineWorkingData_ThisTime();
  464. dataDBlast.GUID = ds.Tables[0].Rows[0][0].ToString(); // 主键
  465. dataDBlast.LineName = ds.Tables[0].Rows[0][1].ToString(); // 线体名称
  466. dataDBlast.BootTimeLong = Convert.ToSingle(ds.Tables[0].Rows[0][2].ToString()); // 本次开机时间(整线)
  467. dataDBlast.CreateTime = Convert.ToDateTime(ds.Tables[0].Rows[0][14].ToString()); // 创建时间
  468. if (lineWorkingData1.BootTimeLong > dataDBlast.BootTimeLong) // 需要更新的情况;不需要更新的走后面的插入
  469. {
  470. dataDBlast.BootTimeLong = lineWorkingData1.BootTimeLong; // 本次开机时间(整线)
  471. dataDBlast.NormalTimeLong = lineWorkingData1.NormalTimeLong; // 本次开机运行时间(整线)
  472. dataDBlast.StandbyTimeLong = lineWorkingData1.StandbyTimeLong; // 本次开机待机时间(整线)
  473. dataDBlast.FaultTimeLong = lineWorkingData1.FaultTimeLong; // 本次开机故障时间(整线)
  474. dataDBlast.MaterialShortageTimeLong = lineWorkingData1.MaterialShortageTimeLong; // 本次开机缺料时间(整线)
  475. dataDBlast.MaintenanceTimeLong = lineWorkingData1.MaintenanceTimeLong; // 本次开机维修时间(整线)
  476. dataDBlast.FaultNumber = lineWorkingData1.FaultNumber; // 本次开机故障停机次数(整线)
  477. dataDBlast.OutputNumber = lineWorkingData1.OutputNumber; // 本次开机产量(整线)
  478. dataDBlast.QualifiedNumber = lineWorkingData1.QualifiedNumber; // 本次开机合格数量(整线)
  479. dataDBlast.QualifiedRate = lineWorkingData1.QualifiedRate; // 本次开机合格率(整线)
  480. dataDBlast.DesignRhythm = lineWorkingData1.DesignRhythm; // 设计节拍(整线)
  481. dataDBlast.RealityRhythm = lineWorkingData1.RealityRhythm; // 本次开机实际节拍(整线)
  482. string usql = dataDBlast.ToStringUpdate();
  483. SQLHelper_New.ExecuteSQL(usql, null);
  484. lineWorkingData1_OldStr = JsonConvert.SerializeObject(dataDBlast);
  485. AddMessage_Station(stationNameStr, LogType.Info, $"更新{BodyRun}完毕![{lineWorkingData1_OldStr}]");
  486. //AddMessage_Station(stationNameStr, LogType.Info, $"更新{BodyRun}完毕!");
  487. }
  488. }
  489. else
  490. {
  491. // 插入
  492. SQLHelper_New.ExecuteSQL(lineWorkingData1.ToStringInsert(), null);
  493. lineWorkingData1_OldStr = String.Copy(lineWorkingData1_Str);
  494. AddMessage_Station(stationNameStr, LogType.Info, $"保存{BodyRun}完毕![{lineWorkingData1_OldStr}]");
  495. //AddMessage_Station(stationNameStr, LogType.Info, $"保存{BodyRun}完毕!");
  496. }
  497. }
  498. else if (!lineWorkingData1_Str.Equals(lineWorkingData1_OldStr)) // 非“软件启动后第一次运行”
  499. {
  500. LineWorkingData_ThisTime lineWorkingData1_Old = string.IsNullOrEmpty(lineWorkingData1_OldStr) ? lineWorkingData1 : JsonConvert.DeserializeObject<LineWorkingData_ThisTime>(lineWorkingData1_OldStr); // 上次的状态信息
  501. //// 本次开机设备运行情况
  502. //LineWorkingData1_ThisTime lineWorkingData_UI = JsonConvert.DeserializeObject<LineWorkingData1_ThisTime>(lineWorkingData1_OldStr);
  503. //Task.Run(() =>
  504. //{
  505. // if (Form_Main.formDevAlarm != null && !Form_Main.formDevAlarm.IsDisposed && Form_Main.formDevAlarm.Visible)
  506. // {
  507. // Form_Main.formDevAlarm.UpdDeviceStatus_ThisTime(lineWorkingData_UI); // UI更新
  508. // }
  509. //});
  510. // 本日设备运行情况
  511. // 存数据库(开机时间>上次的开机时间,则更新上次记录;<则作为新数据插入)
  512. if (lineWorkingData1.BootTimeLong > lineWorkingData1_Old.BootTimeLong)
  513. {
  514. // 更新
  515. lineWorkingData1_Old.BootTimeLong = lineWorkingData1.BootTimeLong; // 本次开机时间(整线)
  516. lineWorkingData1_Old.NormalTimeLong = lineWorkingData1.NormalTimeLong; // 本次开机运行时间(整线)
  517. lineWorkingData1_Old.StandbyTimeLong = lineWorkingData1.StandbyTimeLong; // 本次开机待机时间(整线)
  518. lineWorkingData1_Old.FaultTimeLong = lineWorkingData1.FaultTimeLong; // 本次开机故障时间(整线)
  519. lineWorkingData1_Old.MaterialShortageTimeLong = lineWorkingData1.MaterialShortageTimeLong; // 本次开机缺料时间(整线)
  520. lineWorkingData1_Old.MaintenanceTimeLong = lineWorkingData1.MaintenanceTimeLong; // 本次开机维修时间(整线)
  521. lineWorkingData1_Old.FaultNumber = lineWorkingData1.FaultNumber; // 本次开机故障停机次数(整线)
  522. lineWorkingData1_Old.OutputNumber = lineWorkingData1.OutputNumber; // 本次开机产量(整线)
  523. lineWorkingData1_Old.QualifiedNumber = lineWorkingData1.QualifiedNumber; // 本次开机合格数量(整线)
  524. lineWorkingData1_Old.QualifiedRate = lineWorkingData1.QualifiedRate; // 本次开机合格率(整线)
  525. lineWorkingData1_Old.DesignRhythm = lineWorkingData1.DesignRhythm; // 设计节拍(整线)
  526. lineWorkingData1_Old.RealityRhythm = lineWorkingData1.RealityRhythm; // 本次开机实际节拍(整线)
  527. SQLHelper_New.ExecuteSQL(lineWorkingData1_Old.ToStringUpdate(), null);
  528. lineWorkingData1_OldStr = JsonConvert.SerializeObject(lineWorkingData1_Old);
  529. AddMessage_Station(stationNameStr, LogType.Info, $"更新{BodyRun}完毕![{lineWorkingData1_OldStr}]");
  530. //AddMessage_Station(stationNameStr, LogType.Info, $"更新{BodyRun}完毕!");
  531. }
  532. else if (lineWorkingData1.BootTimeLong < lineWorkingData1_Old.BootTimeLong)
  533. {
  534. // 插入
  535. SQLHelper_New.ExecuteSQL(lineWorkingData1.ToStringInsert(), null);
  536. lineWorkingData1_OldStr = String.Copy(lineWorkingData1_Str);
  537. AddMessage_Station(stationNameStr, LogType.Info, $"保存{BodyRun}完毕![{lineWorkingData1_OldStr}]");
  538. //AddMessage_Station(stationNameStr, LogType.Info, $"保存{BodyRun}完毕!");
  539. }
  540. await Task.Run(() =>
  541. {
  542. try
  543. {
  544. if (Form_Main.formDevAlarm != null && !Form_Main.formDevAlarm.IsDisposed && Form_Main.formDevAlarm.Visible)
  545. {
  546. Form_Main.formDevAlarm.UpdDeviceStatus_Today(); // UI更新
  547. }
  548. }
  549. catch { }
  550. });
  551. }
  552. }
  553. catch (Exception ex)
  554. {
  555. string str = ex.StackTrace;
  556. AddMessage_Station(stationNameStr, LogType.Error, $"PLC1_{stationNameStr}_获取设备运行信息出错!错误信息:" + ex.Message.ToString() + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  557. }
  558. #endregion 获取设备运行信息
  559. #region 报警数据
  560. try
  561. {
  562. List<DeviceAlarm_Cur> deviceAlarm_Curs = new List<DeviceAlarm_Cur>(); // 同步到报警页面用传输载体
  563. bool isNeedUpdUI = false; // 是否需要更新历史报警UI
  564. // 同步“设备报警信息”到“设备报警临时字典DicAlarms_Cur”
  565. var dicAlarms_Cur_PLC1 = DicAlarms_Cur[GlobalContext.LineCode];
  566. for (int i = 0; i < dicAlarms_Cur_PLC1.Count; i++) // 读取
  567. {
  568. short shortBuf = 0;// plc1Alarm.ReadHoldingRegisters<short>(dicAlarms_Cur_PLC1[i].关联的PLC地址);
  569. dicAlarms_Cur_PLC1[i].是否报警 = shortBuf != 0;
  570. if (dicAlarms_Cur_PLC1[i].上次的运行状态 != dicAlarms_Cur_PLC1[i].是否报警)
  571. {
  572. isNeedUpdUI = true; // 需要更新历史报警UI信息
  573. // 记录
  574. dicAlarms_Cur_PLC1[i].上次的运行状态 = dicAlarms_Cur_PLC1[i].是否报警;
  575. switch (dicAlarms_Cur_PLC1[i].是否报警)
  576. {
  577. case true: // 报警
  578. dicAlarms_Cur_PLC1[i].报警数据 = new AlarmData()
  579. {
  580. GUID = Guid.NewGuid().ToString(),
  581. LineName = GlobalContext.LineCode, // 线体
  582. AlarmType = dicAlarms_Cur_PLC1[i].报警类型, // 报警类型
  583. AlarmDesc = dicAlarms_Cur_PLC1[i].报警详情, // 报警内容
  584. StartTime = dtNow // 开始时间
  585. };
  586. // 传输到页面
  587. deviceAlarm_Curs.Add(new DeviceAlarm_Cur()
  588. {
  589. 线体名称 = dicAlarms_Cur_PLC1[i].报警数据.LineName,
  590. 报警类型 = dicAlarms_Cur_PLC1[i].报警数据.AlarmType,
  591. 报警内容 = dicAlarms_Cur_PLC1[i].报警数据.AlarmDesc,
  592. 开始时间 = dtNow
  593. });
  594. // 新增到数据库
  595. var data1 = dicAlarms_Cur_PLC1[i].报警数据;
  596. SaveAlarmDataByDB(stationNameStr, data1, false);
  597. AddMessage_Station(stationNameStr, LogType.Info, $"更新{BodyAlarm}完毕!");
  598. break;
  599. case false: // 消除报警
  600. if (dicAlarms_Cur_PLC1[i].报警数据 == null || string.IsNullOrEmpty(dicAlarms_Cur_PLC1[i].报警数据.GUID))
  601. {
  602. dicAlarms_Cur_PLC1[i].报警数据 = new AlarmData()
  603. {
  604. GUID = Guid.NewGuid().ToString(),
  605. LineName = GlobalContext.LineCode, // 线体
  606. AlarmType = dicAlarms_Cur_PLC1[i].报警类型, // 报警类型
  607. AlarmDesc = dicAlarms_Cur_PLC1[i].报警详情, // 报警内容
  608. StartTime = dtNow, // 开始时间
  609. EndTime = dtNow, // 开始时间
  610. PersistTime = 1, // 耗时1s
  611. };
  612. // 新增
  613. var data2 = dicAlarms_Cur_PLC1[i].报警数据;
  614. SaveAlarmDataByDB(stationNameStr, data2, false);
  615. AddMessage_Station(stationNameStr, LogType.Info, $"更新{BodyAlarm}完毕!");
  616. }
  617. else
  618. {
  619. dicAlarms_Cur_PLC1[i].报警数据.EndTime = dtNow; // 开始时间
  620. dicAlarms_Cur_PLC1[i].报警数据.PersistTime = Convert.ToInt32((dicAlarms_Cur_PLC1[i].报警数据.EndTime
  621. - dicAlarms_Cur_PLC1[i].报警数据.StartTime).TotalSeconds); // 耗时s
  622. // 修改
  623. var data3 = dicAlarms_Cur_PLC1[i].报警数据;
  624. SaveAlarmDataByDB(stationNameStr, data3, true);
  625. AddMessage_Station(stationNameStr, LogType.Info, $"更新{BodyAlarm}完毕!");
  626. }
  627. break;
  628. default:
  629. break;
  630. }
  631. }
  632. }
  633. DicAlarms_Cur[GlobalContext.LineCode] = dicAlarms_Cur_PLC1;
  634. // 有新报警则更新
  635. if (isNeedUpdUI)
  636. {
  637. // UI展示 - 展示到设备状态页
  638. await Task.Run(() =>
  639. {
  640. try
  641. {
  642. if (Form_Main.formDevAlarm != null && !Form_Main.formDevAlarm.IsDisposed)
  643. {
  644. Form_Main.formDevAlarm.UpdDeviceAlarm_Cur(deviceAlarm_Curs); // 报警UI 更新
  645. if (Form_Main.formDevAlarm.Visible)
  646. {
  647. Form_Main.formDevAlarm.UpdDeviceAlarm_History_48H(); // 历史报警UI 更新
  648. }
  649. }
  650. }
  651. catch { }
  652. });
  653. }
  654. }
  655. catch (Exception ex)
  656. {
  657. string str = ex.StackTrace;
  658. AddMessage_Station(stationNameStr, LogType.Error, $"PLC1_{stationNameStr}_获取报警数据出错!错误信息:" + ex.Message.ToString() + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  659. }
  660. #endregion 报警数据
  661. UpdatePLCMonitor(1, -2, 1);
  662. }
  663. else
  664. {
  665. UpdatePLCMonitor(1, -2, 0);
  666. }
  667. }
  668. catch (Exception ex)
  669. {
  670. AddMessage_Station(stationNameStr, LogType.Error, $"PLC1_{stationNameStr}运行出错!错误信息:" + ex.Message.ToString());
  671. }
  672. Thread.Sleep(IntervalAlarm);
  673. }
  674. }
  675. #endregion 轮询PLC
  676. #region 下发订单信息
  677. ///// <summary>
  678. ///// 壳体上料(下发工单)的交互逻辑
  679. ///// </summary>
  680. ///// <param name="no"></param>
  681. ///// <exception cref="NotImplementedException"></exception>
  682. //private void ReadStation_DownOrderInfo(int plcNo)
  683. //{
  684. // // [S1] Tray盘上料装备(板测)
  685. // // [S2] FCT(板测)
  686. // // [S3] 值板机
  687. // // [S4] 取放桁架
  688. // // [S5] Tray盘下料装备
  689. // /// 上位机心跳
  690. // /// 获取设备报警数据与状态信息
  691. // string stationNameStr = "[S0]壳体上料";
  692. // while (true)
  693. // {
  694. // try
  695. // {
  696. // if (!GlobalContext._IsCon_Funs1)
  697. // {
  698. // UpdatePLCMonitor(plcNo, 0);
  699. // continue;
  700. // }
  701. // if (Funs[plcNo].isConnected) // 检查PLC是否已连接上
  702. // {
  703. // #region 壳体上料(下发工单)
  704. // try
  705. // {
  706. // Funs[plcNo].Read_Int_Tag("500", 1, out short[] iiMes0);
  707. // Funs[plcNo].Read_Int_Tag("501", 1, out short[] iiPlc0);
  708. // bool mES_FLAG_1 = iiMes0[0] == 1 ? true : false; // MES_FLAG_1
  709. // bool pLC_Flag_1 = iiPlc0[0] == 1 ? true : false; // PLC_FLAG_1
  710. // // 重置数据和信号
  711. // if (mES_FLAG_1 && pLC_Flag_1) // 1 1
  712. // {
  713. // // 清空写给PLC的数据
  714. // int[] i497 = new int[1] { 0 };
  715. // Funs[plcNo].Write_DInt_Tag("497", 1, i497); // SN号(数字部分)重置信号
  716. // // MES_Flag重置为0
  717. // int[] i500 = new int[1] { 0 };
  718. // Funs[plcNo].Write_DInt_Tag("500", 1, i500); // MES_FLAG_1
  719. // }
  720. // }
  721. // catch (Exception ex)
  722. // {
  723. // string str = ex.StackTrace;
  724. // AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr}下发订单信息运行出错!错误信息:" + ex.Message.ToString() + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  725. // }
  726. // #endregion 壳体上料(下发工单)
  727. // UpdatePLCMonitor(plcNo, 1); // 更新PLC状态的UI // 更新PLC状态的UI
  728. // }
  729. // else
  730. // {
  731. // UpdatePLCMonitor(plcNo, 0); // 更新PLC状态的UI
  732. // AddMessage_Station(stationNameStr, LogType.Info, "PLC" + plcNo.ToString() + "_" + stationNameStr + "连接失败!");
  733. //
  734. // Funs[plcNo].Connect();
  735. // }
  736. // }
  737. // catch (Exception ex)
  738. // {
  739. // UpdatePLCMonitor(plcNo, 0); // 更新PLC状态的UI
  740. // AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr}运行出错!错误信息:" + ex.Message.ToString());
  741. //
  742. // Funs[plcNo].ReConnect();
  743. // }
  744. // Thread.Sleep(IntervalReadPLC);
  745. // }
  746. //}
  747. ///// <summary>
  748. ///// 下发订单信息到PLC
  749. ///// </summary>
  750. ///// <param name="no">PLC编号</param>
  751. //private void DownLoadProductInfo(int plcNo, string stationNameStr = "[S0]壳体上料")
  752. //{
  753. // try
  754. // {
  755. // if (!string.IsNullOrEmpty(GlobalContext.Mtltmrk))
  756. // {
  757. // Funs[plcNo].Write_String_Tag("568", 1, GlobalContext.Mtltmrk); // 产品型号(mtltmrk)
  758. // WritePLCLog(LogType.Debug, GlobalContext.Mtltmrk);
  759. // }
  760. // Funs[plcNo].Write_DInt_Tag("500", 1, new Int32[1] { 1 }); // MES_FLAG_1
  761. // }
  762. // catch (Exception ex)
  763. // {
  764. // string str = ex.StackTrace;
  765. // AddMessage_Station(stationNameStr, LogType.Error, "下发订单信息到PLC失败!" + ex.Message.ToString() + ";异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  766. // }
  767. //}
  768. /// <summary>
  769. /// 下发清料信号
  770. /// </summary>
  771. /// <param name="no">PLC编号</param>
  772. public bool ClearProducts(int plcNo, string stationNameStr = "[S0]壳体上料")
  773. {
  774. try
  775. {
  776. //Funs[plcNo].ReadHoldingRegisters<int>(496); //
  777. AddMessage_Station(stationNameStr, LogType.Info, "下发了清料信号!");
  778. return true;
  779. }
  780. catch (Exception ex)
  781. {
  782. string str = ex.StackTrace;
  783. AddMessage_Station(stationNameStr, LogType.Error, "下发清料信号失败!" + ex.Message.ToString() + ";异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  784. return false;
  785. }
  786. }
  787. #endregion 下发订单信息
  788. #region PLC1 贲流
  789. #region [S1] 壳体清洁上料装备
  790. /// <summary>
  791. /// S1工位的数据- 触发信号上次的值
  792. /// </summary>
  793. private Dictionary<string, object> s1PLCSignal_Old = new Dictionary<string, object>();
  794. /// <summary>
  795. /// S1工位的数据(含触发信号)
  796. /// </summary>
  797. private Dictionary<string, object> s1PLCData = new Dictionary<string, object>();
  798. /// <summary>
  799. /// S1工位的数据- 回写点位
  800. /// </summary>
  801. private Dictionary<string, WriteToPLC_Flag> s1PLCWriteData = new Dictionary<string, WriteToPLC_Flag>();
  802. ///// <summary>
  803. ///// 触发信号
  804. ///// </summary>
  805. //private ManualResetEvent[] MreTasks;
  806. /// <summary>
  807. /// [S1] 壳体清洁上料装备
  808. /// </summary>
  809. /// <param name="plcNo">PLC编号</param>
  810. private void ReadStation_S1(int plcNo)
  811. {
  812. string stationCode = "[S1]";
  813. string stationName = "壳体清洁上料";
  814. string stationNameStr = stationCode + stationName;
  815. string tagBaseName = "g_OP10_MES"; //标签变量名称
  816. string tagMesCommName = "mesCommToPC"; //标签变量名称
  817. string tagAgvCommName = "agvCommFrmPC";
  818. string tagBarsetName = "BarcodeSet";
  819. OP10_MesData_t stPLC_MesData; //PLC的MES数据
  820. (int, string) result;
  821. #region 创建字典 - 赛米可以放在while中,add前查询下存不存在,存在就赋值不存在就add
  822. // 触发信号字典 赋值 - 赛米可以放在while中,add前查询下存不存在,存在就赋值不存在就add
  823. s1PLCSignal_Old.Add("a1PLC_FLAG_VehicleStates", 0); // PLC_FLAG 载具进站查询状态
  824. s1PLCSignal_Old.Add("a1PLC_FLAG_Check", 0); // PLC_FLAG 上料进站校验
  825. s1PLCSignal_Old.Add("a1PLC_FLAG", 0); // PLC_FLAG 出站接口
  826. s1PLCSignal_Old.Add("a1PLC_FLAG_ICT", 0); // PLC_FLAG 将SN发给ICT标机(串口)
  827. s1PLCSignal_Old.Add("a1OEEPLC_FLAG", 0); // PLC_FLAG 节拍接口
  828. s1PLCSignal_Old.Add("a1AGVUpCall", 0); // AGV上料叫agv信号 AGV上料
  829. s1PLCSignal_Old.Add("a1AGVUpEnd", 0); // AGV上料完成信号 AGV上料
  830. s1PLCSignal_Old.Add("a1AGVDownCall", 0); // AGV下料叫agv信号 AGV下料
  831. s1PLCSignal_Old.Add("a1AGVDownEnd", 0); // AGV下料完成信号 AGV下料
  832. // PLC数据字典 赋值 - 赛米可以放在while中,add前查询下存不存在,存在就赋值不存在就add
  833. s1PLCData.Add("a1PLC_FLAG_VehicleStates", 0); // PLC_FLAG 载具进站查询状态
  834. s1PLCData.Add("a1MES_FLAG_VehicleStates", 0); // MES_FLAG
  835. s1PLCData.Add("a1ProductSN_VehicleStates", ""); // 产品SN(载具码)
  836. s1PLCData.Add("a1PLC_FLAG_Check", 0); // PLC_FLAG 上料进站校验
  837. s1PLCData.Add("a1MES_FLAG_Check", 0); // MES_FLAG
  838. s1PLCData.Add("a1ProductSN_Check", ""); // 产品SN(物料码)
  839. s1PLCData.Add("a1PLC_FLAG", 0); // PLC_FLAG 出站接口
  840. s1PLCData.Add("a1MES_FLAG", 0); // MES_FLAG
  841. s1PLCData.Add("a1ProductSN", ""); // 产品SN(载具SN)
  842. s1PLCData.Add("a1PartNo1", ""); // 物料码1(穴位1)
  843. s1PLCData.Add("a1PartNo2", ""); // 物料码2(穴位2)
  844. s1PLCData.Add("a1Result", 0); // 产品结果
  845. s1PLCData.Add("a1PLC_FLAG_ICT", 0); // PLC_FLAG 将SN发给ICT标机(串口)
  846. s1PLCData.Add("a1MES_FLAG_ICT", 0); // MES_FLAG
  847. s1PLCData.Add("a1ProductSN_ICT", ""); // 产品SN(载具SN)
  848. s1PLCData.Add("a1PartNo1_ICT", ""); // 物料码1(穴位1)
  849. s1PLCData.Add("a1PartNo2_ICT", ""); // 物料码2(穴位2)
  850. s1PLCData.Add("a1OEEPLC_FLAG", 0); // PLC_FLAG 节拍接口
  851. s1PLCData.Add("a1OEEMES_FLAG", 0); // MES_FLAG
  852. s1PLCData.Add("a1OEEPartNo", ""); // 物料码(物料码还未绑定载具SN时必填)
  853. s1PLCData.Add("a1OEEVehicleCode", ""); // 载具SN
  854. s1PLCData.Add("a1OEEPartNum", 0); // 穴位号
  855. s1PLCData.Add("a1OEEType", 0); // 节拍类型(plc写入)
  856. s1PLCData.Add("a1AGVUpCall", 0); // AGV上料叫agv信号 AGV上料
  857. s1PLCData.Add("a1AGVUpStart", 0); // AGV上料开始信号
  858. s1PLCData.Add("a1AGVUpEnd", 0); // AGV上料完成信号
  859. s1PLCData.Add("a1AGVDownCall", 0); // AGV下料叫agv信号 AGV下料
  860. s1PLCData.Add("a1AGVDownStart", 0); // AGV下料开始信号
  861. s1PLCData.Add("a1AGVDownEnd", 0); // AGV下料完成信号
  862. #endregion 创建字典 - 赛米可以放在while中,add前查询下存不存在,存在就赋值不存在就add
  863. while (true)
  864. {
  865. try
  866. {
  867. if (!GlobalContext._IsCon_Funs1)
  868. {
  869. UpdatePLCMonitor(1, plcNo, 0);
  870. continue;
  871. }
  872. if (Funs[plcNo].IsConnected) // 检查PLC是否已连接上
  873. {
  874. Stopwatch stopwatch1 = new Stopwatch();
  875. Stopwatch stopwatch2 = new Stopwatch();
  876. stopwatch1.Start();
  877. stopwatch2.Start();
  878. #region 一次性读取所有数据
  879. // 一次性读取所有数据
  880. result = Funs[plcNo].Read_SingleTag<OP10_MesData_t>(tagBaseName, 1, out stPLC_MesData); //读取单个结构体数据
  881. if (result.Item1 != 0)
  882. {
  883. //richTextBox1.AppendText("\n" + strRet);
  884. }
  885. else
  886. {
  887. //richTextBox1.AppendText("\n" + "读取成功");
  888. }
  889. #endregion 一次性读取所有数据
  890. stopwatch2.Stop();
  891. #region 回写操作,写后清空flag
  892. mesCommToPC WriteBackToPLC = new mesCommToPC();
  893. result = Funs[plcNo].Write_SingleTag<mesCommToPC>(tagBaseName +"." + tagMesCommName, 1, WriteBackToPLC); //写入单个结构体数据
  894. #endregion 回写操作,写后清空flag
  895. #region 进站
  896. try
  897. {
  898. if (stPLC_MesData.mesCommFrmPLC.cmd == (byte)eMesCmd.InStation)
  899. {
  900. Task.Run(() => S1进站(plcNo, stationNameStr, stPLC_MesData, tagBaseName + "." + tagMesCommName));
  901. }
  902. }
  903. catch (Exception ex)
  904. {
  905. string str = ex.StackTrace;
  906. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 上料进站出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  907. }
  908. #endregion 进站
  909. #region 出站
  910. try
  911. {
  912. if (stPLC_MesData.mesCommFrmPLC.cmd == (byte)eMesCmd.OutStation)
  913. {
  914. Task.Run(() => S1出站(plcNo, stationNameStr, stPLC_MesData, tagBaseName + "." + tagMesCommName));
  915. }
  916. }
  917. catch (Exception ex)
  918. {
  919. string str = ex.StackTrace;
  920. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 上料进站出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  921. }
  922. #endregion 进站
  923. UpdatePLCMonitor(1, plcNo, 1); // 更新PLC状态的UI // 更新PLC状态的UI
  924. stopwatch1.Stop();
  925. OnMessage(LogType.Info, $"循环读取PLC数据一次,总用时{stopwatch1.ElapsedMilliseconds}ms[读取用时{stopwatch2.ElapsedMilliseconds}ms]");
  926. }
  927. else
  928. {
  929. UpdatePLCMonitor(1, plcNo, 0); // 更新PLC状态的UI
  930. AddMessage_Station(stationNameStr, LogType.Info, "PLC" + plcNo.ToString() + "_" + stationNameStr + "连接失败!");
  931. Funs[plcNo].Connect(); // 重连
  932. }
  933. }
  934. catch (Exception ex)
  935. {
  936. UpdatePLCMonitor(1, plcNo, 0); // 更新PLC状态的UI
  937. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr}运行出错!错误信息:" + ex.Message.ToString());
  938. }
  939. Thread.Sleep(IntervalReadPLC);
  940. }
  941. }
  942. /// <summary>
  943. /// [S1] 壳体清洁上料 - 进站
  944. /// </summary>
  945. /// <param name="plcNo">PLC编号</param>
  946. /// <param name="stationNameStr">工站全称</param>
  947. /// <param name="stPLC_MesData"></param>
  948. /// <param name="tagMesCommName"></param>
  949. private void S1进站(int plcNo, string stationNameStr, OP10_MesData_t stPLC_MesData, string tagMesCommName)
  950. {
  951. int nRet=0;
  952. string strRet = "";
  953. Stopwatch stopwatch1 = new Stopwatch();
  954. Stopwatch stopwatch2 = new Stopwatch();
  955. try
  956. {
  957. stopwatch1.Start();
  958. string sn = (string)stPLC_MesData.BarcodeSet.strProductBarcode; // 产品SN(物料码)
  959. sn = sn.Replace("\0", "");
  960. // 产品SN(物料码)校验
  961. List<TestItem> item = new List<TestItem>();
  962. stopwatch2.Start();
  963. int result = SaveStationInData(stationNameStr, GlobalContext.WorkOrderCode, GlobalContext.Mtltmrk, sn, item);
  964. stopwatch2.Stop();
  965. //指令执行结果 1:OK 110:失败
  966. byte mesResultFrmWeb = (byte)(result == 1 ? 1 : 110);
  967. //进站结果写入PLC
  968. mesCommToPC MesToPLC = new mesCommToPC();
  969. MesToPLC.cmd = 0;
  970. MesToPLC.cmdParam = 0; //指令参数
  971. MesToPLC.cmdResult = mesResultFrmWeb;
  972. (nRet,strRet)=Funs[plcNo].Write_SingleTag<mesCommToPC>(tagMesCommName, 1, MesToPLC);
  973. //3次控制,弹出
  974. if (nRet != 0 )
  975. {
  976. }
  977. }
  978. catch (Exception ex)
  979. {
  980. string str = ex.StackTrace;
  981. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 上料进站校验出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  982. mesCommToPC MesToPLC = new mesCommToPC();
  983. MesToPLC.cmd = 0;
  984. MesToPLC.cmdParam = 0; //指令参数
  985. MesToPLC.cmdResult = 110;
  986. Funs[plcNo].Write_SingleTag<mesCommToPC>(tagMesCommName, 1, MesToPLC);
  987. }
  988. stopwatch1.Stop();
  989. AddMessage(LogType.Info, stationNameStr + "_进站;总用时" + stopwatch1.ElapsedMilliseconds + "ms;调用MES用时" + stopwatch2.ElapsedMilliseconds + "ms");
  990. }
  991. /// <summary>
  992. /// [S1] 壳体清洁上料 - 出站接口
  993. /// </summary>
  994. private void S1出站(int plcNo, string stationNameStr, OP10_MesData_t stPLC_MesData, string tagMesCommName)
  995. {
  996. Stopwatch stopwatch1 = new Stopwatch();
  997. Stopwatch stopwatch2 = new Stopwatch();
  998. try
  999. {
  1000. stopwatch1.Start();
  1001. string workorder_code = GlobalContext.WorkOrderCode; // 工单号
  1002. string batch_num = GlobalContext.BatchNumber; // 批次号
  1003. string mtltmrk = (string)stPLC_MesData.BarcodeSet.strProductBarcode; // 产品条码; // 产品型号
  1004. mtltmrk = mtltmrk.Replace("\0", "");
  1005. string CarrierBarcode = (string)stPLC_MesData.BarcodeSet.strCarrierBarcode; // 载具条码;
  1006. CarrierBarcode = CarrierBarcode.Replace("\0", "");
  1007. int a1Result = (int)stPLC_MesData.iotData.testStatus; // 产品结果
  1008. bool pass = a1Result == 1;
  1009. List<TestItem> items = new List<TestItem>();
  1010. items.Add(new TestItem()
  1011. {
  1012. Parameter_name = "载具码",
  1013. Parameter_value = CarrierBarcode,
  1014. Parameter_unit = ""
  1015. });
  1016. items.Add(new TestItem()
  1017. {
  1018. Parameter_name = "产品码",
  1019. Parameter_value = mtltmrk,
  1020. Parameter_unit = ""
  1021. });
  1022. //绑定载具和产品
  1023. ResponseMessage message = new ResponseMessage();
  1024. message= SQLHelper.InsertCarrierBind(CarrierBarcode, CarrierBarcode, stationNameStr);
  1025. if (message.result==false)
  1026. {
  1027. AddMessage(LogType.Info, stationNameStr + "_载具码与产品码绑定失败");
  1028. }
  1029. //绑定PLC返回MES数据到本地
  1030. int result1 = SwitctProcessData(stationNameStr, items, "", ""
  1031. , workorder_code, batch_num, mtltmrk, "", "", "", pass, CarrierBarcode, "1");
  1032. byte cmdToPC = (byte)(result1 == 1 ? 1 : 110);
  1033. stopwatch2.Start();
  1034. //进站结果写入PLC
  1035. mesCommToPC MesToPLC = new mesCommToPC();
  1036. MesToPLC.cmd = cmdToPC;
  1037. MesToPLC.cmdParam = 0; //指令参数
  1038. MesToPLC.cmdResult = 1;
  1039. Funs[plcNo].Write_SingleTag<mesCommToPC>(tagMesCommName, 1, MesToPLC);
  1040. stopwatch2.Stop();
  1041. WritePLCLog(LogType.Debug, $"PLC{plcNo}_[{stationNameStr}]-Write" + (result1 == 1 ? "成功!" : "失败!"));
  1042. }
  1043. catch (Exception ex)
  1044. {
  1045. stopwatch2.Start();
  1046. mesCommToPC MesToPLC = new mesCommToPC();
  1047. MesToPLC.cmd = 0;
  1048. MesToPLC.cmdParam = 0; //指令参数
  1049. MesToPLC.cmdResult = 110;
  1050. Funs[plcNo].Write_SingleTag<mesCommToPC>(tagMesCommName, 1, MesToPLC);
  1051. stopwatch2.Stop();
  1052. string str = ex.StackTrace;
  1053. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_[{stationNameStr}]上传加工报错!错误信息:" + ex.Message.ToString() + ";异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  1054. }
  1055. stopwatch1.Stop();
  1056. AddMessage(LogType.Info, stationNameStr + "_出站接口;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  1057. }
  1058. //// 上传点检数据_ [S1] Tray盘上料装备(板测)
  1059. //private void DoOneCheckData_Tray盘上料装备(int plcNo, string stationCode, string stationName)
  1060. //{
  1061. // string equipmentCode = GlobalContext.LineCode + "-" + stationCode; // 设备编号
  1062. // string stationNameStr = stationCode + stationName;
  1063. // string processItem = stationName; // 测试项目
  1064. // try
  1065. // {
  1066. // string workorder_code = GlobalContext.WorkOrderCode; // 工单号
  1067. // string accno = "1"; // 工序编号
  1068. // Funs[plcNo].Read_Real_Tag("896", 1, out float[] float0);
  1069. // float travelLimitUp = float0[0]; // 胶圈装配行程设定上限
  1070. // List<OneCheckItem> items = new List<OneCheckItem>()
  1071. // {
  1072. // new OneCheckItem()
  1073. // {
  1074. // Onecheck_name="胶圈装配行程设定上限",
  1075. // Onecheck_content="上限值",
  1076. // Onecheck_result=$"正常|胶圈装配行程设定上限{travelLimitUp} mm"
  1077. // },
  1078. // };
  1079. // OneCheckData oneCheckData = new OneCheckData()
  1080. // {
  1081. // Line_code = GlobalContext.LineCode,
  1082. // Line_name = GlobalContext.LineName,
  1083. // Equipment_code = equipmentCode,
  1084. // Equipment_name = equipmentCode,
  1085. // Workorder_code = workorder_code,
  1086. // Procedure_code = accno,
  1087. // Procedure_name = processItem,
  1088. // Oneckeck_values = items,
  1089. // Onecheck_empcode = "",
  1090. // Onecheck_empname = "",
  1091. // Onecheck_time = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss.fff")
  1092. // };
  1093. // int result1 = SaveOneCheckDataByDBAndSubmit(oneCheckData, equipmentCode, processItem);
  1094. // //int result = result1 == 1 ? 1 : (GlobalContext.IsSendCheckOneData ? 4 : 1);
  1095. // short result = result1 == 1 ? (short)1 : (short)2;
  1096. // // MES_Flag 为4MES报错
  1097. // Funs[plcNo].Write_DInt_Tag("829", 1, new Int32[1] { result });
  1098. // WritePLCLog(LogType.Debug, $"PLC{plcNo}_[{equipmentCode}]{processItem}-Write" + (result == 1 ? "成功!" : "失败!"));
  1099. // }
  1100. // catch (Exception ex)
  1101. // {
  1102. // // MES_Flag 为2上位机报错
  1103. // Funs[plcNo].Write_DInt_Tag("829", 1, new Int32[1] { 2 });
  1104. // string str = ex.StackTrace;
  1105. // AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_[{equipmentCode}]{processItem}点检报错!错误信息:" + ex.Message.ToString() + ";异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  1106. // }
  1107. //}
  1108. // ReadStation_S1_2 节拍接口+AGV
  1109. /// <summary>
  1110. /// [S1] Tray盘上料装备(板测)- 将SN发给ICT标机(串口)
  1111. /// </summary>
  1112. /// <param name="plcNo">PLC编号</param>
  1113. /// <param name="stationNameStr">工站全称</param>
  1114. private void S1将SN发给ICT标机(int plcNo, string stationNameStr)
  1115. {
  1116. Stopwatch stopwatch1 = new Stopwatch();
  1117. Stopwatch stopwatch2 = new Stopwatch();
  1118. try
  1119. {
  1120. stopwatch1.Start();
  1121. string a1ProductSN_ICT = (string)s1PLCData["a1ProductSN_ICT"]; // 产品SN(载具SN)
  1122. a1ProductSN_ICT = a1ProductSN_ICT.Replace("\0", "");
  1123. string a1PartNo1_ICT = (string)s1PLCData["a1PartNo1_ICT"]; // 物料码1(穴位1)
  1124. a1PartNo1_ICT = a1PartNo1_ICT.Replace("\0", "");
  1125. string a1PartNo2_ICT = (string)s1PLCData["a1PartNo2_ICT"]; // 物料码2(穴位2)
  1126. a1PartNo2_ICT = a1PartNo2_ICT.Replace("\0", "");
  1127. // ZS 将SN发给ICT标机(串口)
  1128. short a1MES_FLAG_ICT = 1;
  1129. stopwatch2.Start();
  1130. // MES_Flag
  1131. //Funs[plcNo].WriteMultipleRegisters<short>(2182, a1MES_FLAG_ICT); // 上位机发送1代表OK;2代表失败;4代表上位机报警;
  1132. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  1133. writeToPLC_Flag.Name = "a1MES_FLAG_ICT";
  1134. writeToPLC_Flag.Adress = 2182;
  1135. writeToPLC_Flag.Value = a1MES_FLAG_ICT;
  1136. SxPLCWriteData_Add(ref s1PLCWriteData, "a1MES_FLAG_ICT", writeToPLC_Flag);
  1137. stopwatch2.Stop();
  1138. }
  1139. catch (Exception ex)
  1140. {
  1141. string str = ex.StackTrace;
  1142. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 将SN发给ICT标机出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  1143. stopwatch2.Start();
  1144. // MES_Flag
  1145. //Funs[plcNo].WriteMultipleRegisters<short>(2182, (short)4); // 4代表上位机报警
  1146. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  1147. writeToPLC_Flag.Name = "a1MES_FLAG_ICT";
  1148. writeToPLC_Flag.Adress = 2182;
  1149. writeToPLC_Flag.Value = (short)4;
  1150. SxPLCWriteData_Add(ref s1PLCWriteData, "a1MES_FLAG_ICT", writeToPLC_Flag);
  1151. stopwatch2.Stop();
  1152. }
  1153. stopwatch1.Stop();
  1154. AddMessage(LogType.Info, stationNameStr + "_将SN发给ICT标机;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  1155. }
  1156. /// <summary>
  1157. /// [S1] Tray盘上料装备(板测)- 节拍接口
  1158. /// </summary>
  1159. /// <param name="plcNo">PLC编号</param>
  1160. /// <param name="stationNameStr">工站全称</param>
  1161. private void S1节拍接口(int plcNo, string stationNameStr)
  1162. {
  1163. Stopwatch stopwatch1 = new Stopwatch();
  1164. Stopwatch stopwatch2 = new Stopwatch();
  1165. string resultStr = string.Empty;
  1166. try
  1167. {
  1168. stopwatch1.Start();
  1169. string oEEType = ((int)s1PLCData["a1OEEType"]).ToString(); // 节拍类型(plc写入)
  1170. string a1OEEPartNo = (string)s1PLCData["a1OEEPartNo"]; // 物料码
  1171. a1OEEPartNo = a1OEEPartNo.Replace("\0", "");
  1172. string a1OEEVehicleCode = (string)s1PLCData["a1OEEVehicleCode"]; // 载具SN
  1173. a1OEEVehicleCode = a1OEEVehicleCode.Replace("\0", "");
  1174. string a1OEEPartNum = ((int)s1PLCData["a1OEEPartNum"]).ToString(); // 穴位号
  1175. a1OEEPartNum = a1OEEPartNum.Replace("\0", "");
  1176. bool actionBool = Enum.TryParse(oEEType, out XiaomiDeviceOEE deviceOEE);
  1177. if (!actionBool)
  1178. {
  1179. stopwatch2.Start();
  1180. // MES_Flag
  1181. //Funs[plcNo].WriteMultipleRegisters<short>(2254, (short)1); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  1182. WriteToPLC_Flag writeToPLC_Flag1 = new WriteToPLC_Flag(); // MES_Flag
  1183. writeToPLC_Flag1.Name = "a1OEEMES_FLAG";
  1184. writeToPLC_Flag1.Adress = 2254;
  1185. writeToPLC_Flag1.Value = (short)1;
  1186. SxPLCWriteData_Add(ref s1PLCWriteData, "a1OEEMES_FLAG", writeToPLC_Flag1);
  1187. stopwatch2.Stop();
  1188. AddMessage(LogType.Info, stationNameStr + $"_节拍接口-- 设备上传了未识别的节拍类型【{oEEType}】请检查;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  1189. return;
  1190. }
  1191. if (string.IsNullOrEmpty(a1OEEPartNo) && string.IsNullOrEmpty(a1OEEVehicleCode))
  1192. {
  1193. stopwatch2.Start();
  1194. // MES_Flag
  1195. //Funs[plcNo].WriteMultipleRegisters<short>(2254, (short)1); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  1196. WriteToPLC_Flag writeToPLC_Flag2 = new WriteToPLC_Flag(); // MES_Flag
  1197. writeToPLC_Flag2.Name = "a1OEEMES_FLAG";
  1198. writeToPLC_Flag2.Adress = 2254;
  1199. writeToPLC_Flag2.Value = (short)1;
  1200. SxPLCWriteData_Add(ref s1PLCWriteData, "a1OEEMES_FLAG", writeToPLC_Flag2);
  1201. stopwatch2.Stop();
  1202. AddMessage(LogType.Info, stationNameStr + $"_节拍接口-- 上传内容无效已自动省略;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  1203. return;
  1204. }
  1205. else if (string.IsNullOrEmpty(a1OEEPartNo) && !string.IsNullOrEmpty(a1OEEVehicleCode))
  1206. { // 查产品SN
  1207. a1OEEPartNo = "Test"; // ZS
  1208. }
  1209. short a1OEEMES_FLAG = 0;
  1210. // 上传OEE
  1211. (short, string) result = SaveOEEData(plcNo, stationNameStr, deviceOEE, a1OEEPartNo, a1OEEVehicleCode);
  1212. a1OEEMES_FLAG = result.Item1;
  1213. resultStr = result.Item2;
  1214. stopwatch2.Start();
  1215. // MES_Flag
  1216. //Funs[plcNo].WriteMultipleRegisters<short>(2254, a1OEEMES_FLAG); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  1217. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  1218. writeToPLC_Flag.Name = "a1OEEMES_FLAG";
  1219. writeToPLC_Flag.Adress = 2254;
  1220. writeToPLC_Flag.Value = a1OEEMES_FLAG;
  1221. SxPLCWriteData_Add(ref s1PLCWriteData, "a1OEEMES_FLAG", writeToPLC_Flag);
  1222. stopwatch2.Stop();
  1223. }
  1224. catch (Exception ex)
  1225. {
  1226. string str = ex.StackTrace;
  1227. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 节拍接口出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  1228. // MES_Flag
  1229. stopwatch2.Start();
  1230. //Funs[plcNo].WriteMultipleRegisters<short>(2254, (short)4); // 4代表上位机报警
  1231. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  1232. writeToPLC_Flag.Name = "a1OEEMES_FLAG";
  1233. writeToPLC_Flag.Adress = 2254;
  1234. writeToPLC_Flag.Value = (short)4;
  1235. SxPLCWriteData_Add(ref s1PLCWriteData, "a1OEEMES_FLAG", writeToPLC_Flag);
  1236. stopwatch2.Stop();
  1237. }
  1238. stopwatch1.Stop();
  1239. AddMessage(LogType.Info, stationNameStr + $"_节拍接口-- {resultStr};总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  1240. }
  1241. /// <summary>
  1242. /// [S1] Tray盘上料装备(板测)- AGV上料叫agv
  1243. /// </summary>
  1244. /// <param name="plcNo">PLC编号</param>
  1245. /// <param name="stationNameStr">工站全称</param>
  1246. private void S1AGV上料叫agv(int plcNo, string stationNameStr)
  1247. {
  1248. Stopwatch stopwatch1 = new Stopwatch();
  1249. Stopwatch stopwatch2 = new Stopwatch();
  1250. try
  1251. {
  1252. stopwatch1.Start();
  1253. // ZS 呼叫AGV
  1254. short a1AGVUpCall = 2;
  1255. stopwatch2.Start();
  1256. // a1AGVUpCall
  1257. //Funs[plcNo].WriteMultipleRegisters<short>(2307, a1AGVUpCall); // 1:plc请求上料(plc请求);10秒响应清证明上位机掉线;2:调用成功(上位机返回);3:AGV报警(上位机返回);4:上位机报警(上位机返回);
  1258. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  1259. writeToPLC_Flag.Name = "a1AGVUpCall";
  1260. writeToPLC_Flag.Adress = 2307;
  1261. writeToPLC_Flag.Value = a1AGVUpCall;
  1262. SxPLCWriteData_Add(ref s1PLCWriteData, "a1AGVUpCall", writeToPLC_Flag);
  1263. stopwatch2.Stop();
  1264. }
  1265. catch (Exception ex)
  1266. {
  1267. string str = ex.StackTrace;
  1268. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} AGV上料叫agv出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  1269. // a1AGVUpCall
  1270. stopwatch2.Start();
  1271. //Funs[plcNo].WriteMultipleRegisters<short>(2307, (short)4); // 4代表上位机报警
  1272. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  1273. writeToPLC_Flag.Name = "a1AGVUpCall";
  1274. writeToPLC_Flag.Adress = 2307;
  1275. writeToPLC_Flag.Value = (short)4;
  1276. SxPLCWriteData_Add(ref s1PLCWriteData, "a1AGVUpCall", writeToPLC_Flag);
  1277. stopwatch2.Stop();
  1278. }
  1279. stopwatch1.Stop();
  1280. AddMessage(LogType.Info, stationNameStr + "_AGV上料叫agv;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  1281. }
  1282. /// <summary>
  1283. /// [S1] Tray盘上料装备(板测)- AGV上料完成
  1284. /// </summary>
  1285. /// <param name="plcNo">PLC编号</param>
  1286. /// <param name="stationNameStr">工站全称</param>
  1287. private void S1AGV上料完成(int plcNo, string stationNameStr)
  1288. {
  1289. Stopwatch stopwatch1 = new Stopwatch();
  1290. Stopwatch stopwatch2 = new Stopwatch();
  1291. try
  1292. {
  1293. stopwatch1.Start();
  1294. // ZS AGV上料完成,让小车离开
  1295. short a1AGVUpEnd = 2;
  1296. stopwatch2.Start();
  1297. // a1AGVUpEnd
  1298. //Funs[plcNo].WriteMultipleRegisters<short>(2309, a1AGVUpEnd); // 1:plc通知完成结果(plc请求);2:调用成功(上位机返回);3:AGV报警(上位机返回);4:上位机报警(上位机返回);
  1299. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  1300. writeToPLC_Flag.Name = "a1AGVUpEnd";
  1301. writeToPLC_Flag.Adress = 2309;
  1302. writeToPLC_Flag.Value = a1AGVUpEnd;
  1303. SxPLCWriteData_Add(ref s1PLCWriteData, "a1AGVUpEnd", writeToPLC_Flag);
  1304. stopwatch2.Stop();
  1305. }
  1306. catch (Exception ex)
  1307. {
  1308. string str = ex.StackTrace;
  1309. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} AGV上料完成出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  1310. // a1AGVUpEnd
  1311. stopwatch2.Start();
  1312. //Funs[plcNo].WriteMultipleRegisters<short>(2309, (short)4); // 4代表上位机报警
  1313. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  1314. writeToPLC_Flag.Name = "a1AGVUpEnd";
  1315. writeToPLC_Flag.Adress = 2309;
  1316. writeToPLC_Flag.Value = (short)4;
  1317. SxPLCWriteData_Add(ref s1PLCWriteData, "a1AGVUpEnd", writeToPLC_Flag);
  1318. stopwatch2.Stop();
  1319. }
  1320. stopwatch1.Stop();
  1321. AddMessage(LogType.Info, stationNameStr + "_AGV上料完成;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  1322. }
  1323. /// <summary>
  1324. /// [S1] Tray盘上料装备(板测)- AGV下料叫agv
  1325. /// </summary>
  1326. /// <param name="plcNo">PLC编号</param>
  1327. /// <param name="stationNameStr">工站全称</param>
  1328. private void S1AGV下料叫agv(int plcNo, string stationNameStr)
  1329. {
  1330. Stopwatch stopwatch1 = new Stopwatch();
  1331. Stopwatch stopwatch2 = new Stopwatch();
  1332. try
  1333. {
  1334. stopwatch1.Start();
  1335. // ZS 呼叫AGV
  1336. short a1AGVDownCall = 2;
  1337. stopwatch2.Start();
  1338. // a1AGVDownCall
  1339. //Funs[plcNo].WriteMultipleRegisters<short>(2320, a1AGVDownCall); // 1:plc请求下料(plc请求);10秒响应清证明上位机掉线;2:调用成功(上位机返回);3:AGV报警(上位机返回);4:上位机报警(上位机返回);
  1340. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  1341. writeToPLC_Flag.Name = "a1AGVDownCall";
  1342. writeToPLC_Flag.Adress = 2320;
  1343. writeToPLC_Flag.Value = a1AGVDownCall;
  1344. SxPLCWriteData_Add(ref s1PLCWriteData, "a1AGVDownCall", writeToPLC_Flag);
  1345. stopwatch2.Stop();
  1346. }
  1347. catch (Exception ex)
  1348. {
  1349. string str = ex.StackTrace;
  1350. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} AGV下料叫agv出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  1351. // a1AGVDownCall
  1352. stopwatch2.Start();
  1353. //Funs[plcNo].WriteMultipleRegisters<short>(2320, (short)4); // 4代表上位机报警
  1354. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  1355. writeToPLC_Flag.Name = "a1AGVDownCall";
  1356. writeToPLC_Flag.Adress = 2320;
  1357. writeToPLC_Flag.Value = (short)4;
  1358. SxPLCWriteData_Add(ref s1PLCWriteData, "a1AGVDownCall", writeToPLC_Flag);
  1359. stopwatch2.Stop();
  1360. }
  1361. stopwatch1.Stop();
  1362. AddMessage(LogType.Info, stationNameStr + "_AGV下料叫agv;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  1363. }
  1364. /// <summary>
  1365. /// [S1] Tray盘上料装备(板测)- AGV下料完成
  1366. /// </summary>
  1367. /// <param name="plcNo">PLC编号</param>
  1368. /// <param name="stationNameStr">工站全称</param>
  1369. private void S1AGV下料完成(int plcNo, string stationNameStr)
  1370. {
  1371. Stopwatch stopwatch1 = new Stopwatch();
  1372. Stopwatch stopwatch2 = new Stopwatch();
  1373. try
  1374. {
  1375. stopwatch1.Start();
  1376. // ZS AGV上料完成,让小车离开
  1377. short a1AGVDownEnd = 2;
  1378. stopwatch2.Start();
  1379. // a1AGVDownEnd
  1380. //Funs[plcNo].WriteMultipleRegisters<short>(2322, a1AGVDownEnd); // 1:plc通知完成结果(plc请求);2:调用成功(上位机返回);3:AGV报警(上位机返回);4:上位机报警(上位机返回);
  1381. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  1382. writeToPLC_Flag.Name = "a1AGVDownEnd";
  1383. writeToPLC_Flag.Adress = 2322;
  1384. writeToPLC_Flag.Value = a1AGVDownEnd;
  1385. SxPLCWriteData_Add(ref s1PLCWriteData, "a1AGVDownEnd", writeToPLC_Flag);
  1386. stopwatch2.Stop();
  1387. }
  1388. catch (Exception ex)
  1389. {
  1390. string str = ex.StackTrace;
  1391. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} AGV下料完成出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  1392. // a1AGVDownEnd
  1393. stopwatch2.Start();
  1394. //Funs[plcNo].WriteMultipleRegisters<short>(2322, (short)4); // 4代表上位机报警
  1395. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  1396. writeToPLC_Flag.Name = "a1AGVDownEnd";
  1397. writeToPLC_Flag.Adress = 2322;
  1398. writeToPLC_Flag.Value = (short)4;
  1399. SxPLCWriteData_Add(ref s1PLCWriteData, "a1AGVDownEnd", writeToPLC_Flag);
  1400. stopwatch2.Stop();
  1401. }
  1402. stopwatch1.Stop();
  1403. AddMessage(LogType.Info, stationNameStr + "_AGV下料完成;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  1404. }
  1405. #endregion [S1] Tray盘上料装备(板测)
  1406. #endregion PLC1 张超凡
  1407. #region PLC2 贲流
  1408. #region [S2] 上盖板上料装备
  1409. /// <summary>
  1410. /// S2工位的数据- 触发信号上次的值
  1411. /// </summary>
  1412. private Dictionary<string, object> s2PLCSignal_Old = new Dictionary<string, object>();
  1413. /// <summary>
  1414. /// S2工位的数据(含触发信号)
  1415. /// </summary>
  1416. private Dictionary<string, object> s2PLCData = new Dictionary<string, object>();
  1417. /// <summary>
  1418. /// S2工位的数据- 回写点位
  1419. /// </summary>
  1420. private Dictionary<string, WriteToPLC_Flag> s2PLCWriteData = new Dictionary<string, WriteToPLC_Flag>();
  1421. /// <summary>
  1422. /// [S2] FCT(板测)
  1423. /// </summary>
  1424. /// <param name="plcNo">PLC编号</param>
  1425. private void ReadStation_S2(int plcNo)
  1426. {
  1427. string stationCode = "[S2]";
  1428. string stationName = "上盖板上料装备";
  1429. string stationNameStr = stationCode + stationName;
  1430. string tagBaseName = "g_OP20_MES"; //标签变量名称
  1431. string tagMesCommName = "mesCommToPC"; //标签变量名称
  1432. string tagAgvCommName = "agvCommFrmPC";
  1433. string tagBarsetName = "BarcodeSet";
  1434. OP20_MesData_t stPLC_MesData; //PLC的MES数据
  1435. (int, string) result;
  1436. while (true)
  1437. {
  1438. try
  1439. {
  1440. if (!GlobalContext._IsCon_Funs2)
  1441. {
  1442. UpdatePLCMonitor(1, plcNo, 0);
  1443. continue;
  1444. }
  1445. if (Funs[plcNo].IsConnected) // 检查PLC是否已连接上
  1446. {
  1447. Stopwatch stopwatch1 = new Stopwatch();
  1448. Stopwatch stopwatch2 = new Stopwatch();
  1449. stopwatch1.Start();
  1450. stopwatch2.Start();
  1451. #region 一次性读取所有数据
  1452. // 一次性读取所有数据
  1453. result = Funs[plcNo].Read_SingleTag<OP20_MesData_t>(tagBaseName, 1, out stPLC_MesData); //读取单个结构体数据
  1454. if (result.Item1 != 0)
  1455. {
  1456. //richTextBox1.AppendText("\n" + strRet);
  1457. }
  1458. else
  1459. {
  1460. //richTextBox1.AppendText("\n" + "读取成功");
  1461. }
  1462. #endregion 一次性读取所有数据
  1463. stopwatch2.Stop();
  1464. #region 回写操作,写后清空flag
  1465. mesCommToPC WriteBackToPLC = new mesCommToPC();
  1466. result = Funs[plcNo].Write_SingleTag<mesCommToPC>(tagBaseName + "." + tagMesCommName, 1, WriteBackToPLC); //写入单个结构体数据
  1467. #endregion 回写操作,写后清空flag
  1468. #region 进站
  1469. try
  1470. {
  1471. if (stPLC_MesData.mesCommFrmPLC.cmd == (byte)eMesCmd.InStation)
  1472. {
  1473. Task.Run(() => S2进站(plcNo, stationNameStr, stPLC_MesData, tagBaseName + "." + tagMesCommName, tagBaseName + "." + tagBarsetName));
  1474. //进站
  1475. }
  1476. }
  1477. catch (Exception ex)
  1478. {
  1479. //Funs[plcNo].WriteMultipleRegisters<short>(2003, (short)6); // 6代表上位机报警
  1480. string str = ex.StackTrace;
  1481. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 进站校验出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  1482. }
  1483. #endregion 进站
  1484. #region 出站
  1485. try
  1486. {
  1487. if (stPLC_MesData.mesCommFrmPLC.cmd == (byte)eMesCmd.OutStation)
  1488. {
  1489. Task.Run(() => S2出站(plcNo, stationNameStr, stPLC_MesData, tagBaseName + "." + tagMesCommName));
  1490. }
  1491. }
  1492. catch (Exception ex)
  1493. {
  1494. string str = ex.StackTrace;
  1495. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 上料进站出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  1496. }
  1497. #endregion 出站
  1498. UpdatePLCMonitor(1, plcNo, 1); // 更新PLC状态的UI // 更新PLC状态的UI
  1499. stopwatch1.Stop();
  1500. //if (stopwatch1.ElapsedMilliseconds > 60) // ZS 稳定后取消注释该项
  1501. OnMessage(LogType.Info, $"循环读取PLC数据一次,总用时{stopwatch1.ElapsedMilliseconds}ms[读取用时{stopwatch2.ElapsedMilliseconds}ms]");
  1502. }
  1503. else
  1504. {
  1505. UpdatePLCMonitor(1, plcNo, 0); // 更新PLC状态的UI
  1506. AddMessage_Station(stationNameStr, LogType.Info, "PLC" + plcNo.ToString() + "_" + stationNameStr + "连接失败!");
  1507. Funs[plcNo].Connect();
  1508. }
  1509. }
  1510. catch (Exception ex)
  1511. {
  1512. UpdatePLCMonitor(1, plcNo, 0); // 更新PLC状态的UI
  1513. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr}运行出错!错误信息:" + ex.Message.ToString());
  1514. //Funs[plcNo].ReConnect();
  1515. }
  1516. Thread.Sleep(IntervalReadPLC);
  1517. }
  1518. }
  1519. /// <summary>
  1520. /// [S2] 上盖板上料装备
  1521. /// </summary>
  1522. /// <param name="plcNo">PLC编号</param>
  1523. /// <param name="stationNameStr">工站全称</param>
  1524. private void S2进站(int plcNo, string stationNameStr, OP20_MesData_t stPLC_MesData, string tagMesCommName,string tagBarsetName)
  1525. {
  1526. Stopwatch stopwatch1 = new Stopwatch();
  1527. Stopwatch stopwatch2 = new Stopwatch();
  1528. try
  1529. {
  1530. stopwatch1.Start();
  1531. string sn = (string)stPLC_MesData.BarcodeSet.strProductBarcode; // 产品SN(物料码)
  1532. sn = sn.Replace("\0", "");
  1533. string strCarrierBarcode = (string)stPLC_MesData.BarcodeSet.strCarrierBarcode; // 产品SN(物料码)
  1534. strCarrierBarcode = strCarrierBarcode.Replace("\0", "");
  1535. //载具码验证产品码 错误码111
  1536. string strProductBarcode = SQLHelper.GetProductBarcodeByCarrierCode(strCarrierBarcode);
  1537. if (string.IsNullOrEmpty(strProductBarcode))
  1538. {
  1539. AddMessage_Station(stationNameStr, LogType.Error, $"PLC S2 上盖板上料装备未能成功绑定载具信息");
  1540. }
  1541. if (!string.IsNullOrEmpty(strProductBarcode) && !string.IsNullOrEmpty(sn) && strProductBarcode!=sn)
  1542. {
  1543. AddMessage_Station(stationNameStr, LogType.Error, $"PLC S2 上盖板上料装备未能成功绑定载具信息");
  1544. }
  1545. // 产品SN(物料码)校验
  1546. List <TestItem> item = new List<TestItem>();
  1547. stopwatch2.Start();
  1548. int result = SaveStationInData(stationNameStr, GlobalContext.WorkOrderCode, GlobalContext.Mtltmrk, sn, item);
  1549. stopwatch2.Stop();
  1550. //指令执行结果 1:OK 110:失败
  1551. byte cmdToPC = (byte)(result == 1 ? 1 : 110);
  1552. //进站结果写入PLC
  1553. mesCommToPC MesToPLC = new mesCommToPC();
  1554. MesToPLC.cmd = cmdToPC;
  1555. MesToPLC.cmdParam = 0; //指令参数
  1556. MesToPLC.cmdResult = 1;
  1557. Funs[plcNo].Write_SingleTag<mesCommToPC>(tagMesCommName, 1, MesToPLC);
  1558. if (string.IsNullOrEmpty(sn))
  1559. {
  1560. BarcodeSet_t BarcodeToPlc= new BarcodeSet_t();
  1561. BarcodeToPlc.strCarrierBarcode = strCarrierBarcode;
  1562. BarcodeToPlc.strProductBarcode = sn;
  1563. Funs[plcNo].Write_SingleTag<BarcodeSet_t>(tagBarsetName, 1, BarcodeToPlc);
  1564. }
  1565. }
  1566. catch (Exception ex)
  1567. {
  1568. string str = ex.StackTrace;
  1569. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 上料进站校验出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  1570. mesCommToPC MesToPLC = new mesCommToPC();
  1571. MesToPLC.cmd = 0;
  1572. MesToPLC.cmdParam = 0; //指令参数
  1573. MesToPLC.cmdResult = 110;
  1574. Funs[plcNo].Write_SingleTag<mesCommToPC>(tagMesCommName, 1, MesToPLC);
  1575. }
  1576. stopwatch1.Stop();
  1577. AddMessage(LogType.Info, stationNameStr + "_进站;总用时" + stopwatch1.ElapsedMilliseconds + "ms;调用MES用时" + stopwatch2.ElapsedMilliseconds + "ms");
  1578. }
  1579. /// <summary>
  1580. /// [S2] 上盖板上料装备 - 出站接口
  1581. /// </summary>
  1582. private void S2出站(int plcNo, string stationNameStr, OP20_MesData_t stPLC_MesData, string tagMesCommName)
  1583. {
  1584. Stopwatch stopwatch1 = new Stopwatch();
  1585. Stopwatch stopwatch2 = new Stopwatch();
  1586. try
  1587. {
  1588. stopwatch1.Start();
  1589. string workorder_code = GlobalContext.WorkOrderCode; // 工单号
  1590. string batch_num = GlobalContext.BatchNumber; // 批次号
  1591. string mtltmrk = (string)stPLC_MesData.BarcodeSet.strProductBarcode; // 产品条码; // 产品型号
  1592. mtltmrk = mtltmrk.Replace("\0", "");
  1593. string CarrierBarcode = (string)stPLC_MesData.BarcodeSet.strCarrierBarcode; // 载具条码;
  1594. CarrierBarcode = CarrierBarcode.Replace("\0", "");
  1595. int a1Result = (int)stPLC_MesData.iotData.testStatus; // 产品结果
  1596. bool pass = a1Result == 1;
  1597. List<TestItem> items = new List<TestItem>();
  1598. items.Add(new TestItem()
  1599. {
  1600. Parameter_name = "载具码",
  1601. Parameter_value = CarrierBarcode,
  1602. Parameter_unit = ""
  1603. });
  1604. items.Add(new TestItem()
  1605. {
  1606. Parameter_name = "产品码",
  1607. Parameter_value = mtltmrk,
  1608. Parameter_unit = ""
  1609. });
  1610. //保存PLC返回MES数据到本地
  1611. int result1 = SwitctProcessData(stationNameStr, items, "", ""
  1612. , workorder_code, batch_num, mtltmrk, "", "", "", pass, CarrierBarcode, "1");
  1613. byte cmdToPC = (byte)(result1 == 1 ? 1 : 110);
  1614. stopwatch2.Start();
  1615. //进站结果写入PLC
  1616. mesCommToPC MesToPLC = new mesCommToPC();
  1617. MesToPLC.cmd = cmdToPC;
  1618. MesToPLC.cmdParam = 0; //指令参数
  1619. MesToPLC.cmdResult = 1;
  1620. Funs[plcNo].Write_SingleTag<mesCommToPC>(tagMesCommName, 1, MesToPLC);
  1621. stopwatch2.Stop();
  1622. WritePLCLog(LogType.Debug, $"PLC{plcNo}_[{stationNameStr}]-Write" + (result1 == 1 ? "成功!" : "失败!"));
  1623. }
  1624. catch (Exception ex)
  1625. {
  1626. stopwatch2.Start();
  1627. mesCommToPC MesToPLC = new mesCommToPC();
  1628. MesToPLC.cmd = 0;
  1629. MesToPLC.cmdParam = 0; //指令参数
  1630. MesToPLC.cmdResult = 110;
  1631. Funs[plcNo].Write_SingleTag<mesCommToPC>(tagMesCommName, 1, MesToPLC);
  1632. stopwatch2.Stop();
  1633. string str = ex.StackTrace;
  1634. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_[{stationNameStr}]上传加工报错!错误信息:" + ex.Message.ToString() + ";异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  1635. }
  1636. stopwatch1.Stop();
  1637. AddMessage(LogType.Info, stationNameStr + "_出站接口;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  1638. }
  1639. /// <summary>
  1640. /// [S2] FCT(板测)- 节拍接口
  1641. /// </summary>
  1642. /// <param name="plcNo">PLC编号</param>
  1643. /// <param name="stationNameStr">工站全称</param>
  1644. private void S2节拍接口(int plcNo, string stationNameStr)
  1645. {
  1646. Stopwatch stopwatch1 = new Stopwatch();
  1647. Stopwatch stopwatch2 = new Stopwatch();
  1648. string resultStr = string.Empty;
  1649. try
  1650. {
  1651. stopwatch1.Start();
  1652. string oEEType = ((int)s2PLCData["b1OEEType"]).ToString(); // 节拍类型(plc写入)
  1653. string b1OEEProductSN = (string)s2PLCData["b1OEEProductSN"]; // 载具SN
  1654. bool actionBool = Enum.TryParse(oEEType, out XiaomiDeviceOEE deviceOEE);
  1655. if (!actionBool)
  1656. {
  1657. stopwatch2.Start();
  1658. // MES_Flag
  1659. //Funs[plcNo].WriteMultipleRegisters<short>(2203, (short)4); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  1660. WriteToPLC_Flag writeToPLC_Flag1 = new WriteToPLC_Flag(); // MES_Flag
  1661. writeToPLC_Flag1.Name = "b1OEEMES_FLAG";
  1662. writeToPLC_Flag1.Adress = 2203;
  1663. writeToPLC_Flag1.Value = (short)4;
  1664. SxPLCWriteData_Add(ref s2PLCWriteData, "b1OEEMES_FLAG", writeToPLC_Flag1);
  1665. stopwatch2.Stop();
  1666. AddMessage(LogType.Info, stationNameStr + $"_节拍接口-- 设备上传了未识别的节拍类型【{oEEType}】请检查;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  1667. return;
  1668. }
  1669. string b1OEEPartNo = string.Empty; // 物料码
  1670. if (string.IsNullOrEmpty(b1OEEProductSN))
  1671. {
  1672. stopwatch2.Start();
  1673. // MES_Flag
  1674. //Funs[plcNo].WriteMultipleRegisters<short>(2203, (short)1); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  1675. WriteToPLC_Flag writeToPLC_Flag1 = new WriteToPLC_Flag(); // MES_Flag
  1676. writeToPLC_Flag1.Name = "b1OEEMES_FLAG";
  1677. writeToPLC_Flag1.Adress = 2203;
  1678. writeToPLC_Flag1.Value = (short)1;
  1679. SxPLCWriteData_Add(ref s2PLCWriteData, "b1OEEMES_FLAG", writeToPLC_Flag1);
  1680. stopwatch2.Stop();
  1681. AddMessage(LogType.Info, stationNameStr + $"_节拍接口-- 上传内容无效已自动省略;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  1682. return;
  1683. }
  1684. else
  1685. { // 查产品SN
  1686. b1OEEPartNo = "Test"; // ZS
  1687. }
  1688. short b1OEEMES_FLAG = 0;
  1689. // 上传OEE
  1690. (short, string) result = SaveOEEData(plcNo, stationNameStr, deviceOEE, b1OEEPartNo, b1OEEProductSN);
  1691. b1OEEMES_FLAG = result.Item1;
  1692. resultStr = result.Item2;
  1693. stopwatch2.Start();
  1694. // MES_Flag
  1695. //Funs[plcNo].WriteMultipleRegisters<short>(2203, b1OEEMES_FLAG); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  1696. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  1697. writeToPLC_Flag.Name = "b1OEEMES_FLAG";
  1698. writeToPLC_Flag.Adress = 2203;
  1699. writeToPLC_Flag.Value = b1OEEMES_FLAG;
  1700. SxPLCWriteData_Add(ref s2PLCWriteData, "b1OEEMES_FLAG", writeToPLC_Flag);
  1701. stopwatch2.Stop();
  1702. }
  1703. catch (Exception ex)
  1704. {
  1705. string str = ex.StackTrace;
  1706. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 节拍接口出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  1707. // MES_Flag
  1708. stopwatch2.Start();
  1709. //Funs[plcNo].WriteMultipleRegisters<short>(2203, (short)4); // 4代表上位机报警
  1710. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  1711. writeToPLC_Flag.Name = "b1OEEMES_FLAG";
  1712. writeToPLC_Flag.Adress = 2203;
  1713. writeToPLC_Flag.Value = (short)4;
  1714. SxPLCWriteData_Add(ref s2PLCWriteData, "b1OEEMES_FLAG", writeToPLC_Flag);
  1715. stopwatch2.Stop();
  1716. }
  1717. stopwatch1.Stop();
  1718. AddMessage(LogType.Info, stationNameStr + $"_节拍接口-- {resultStr};总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  1719. }
  1720. #endregion [S2] FCT(板测)
  1721. #endregion PLC2 李晓奇
  1722. #region PLC3 刘永村
  1723. #region [S3] 值板机
  1724. /// <summary>
  1725. /// S3工位的数据- 触发信号上次的值
  1726. /// </summary>
  1727. private Dictionary<string, object> s3PLCSignal_Old = new Dictionary<string, object>();
  1728. /// <summary>
  1729. /// S3工位的数据(含触发信号)
  1730. /// </summary>
  1731. private Dictionary<string, object> s3PLCData = new Dictionary<string, object>();
  1732. /// <summary>
  1733. /// S3工位的数据- 回写点位
  1734. /// </summary>
  1735. private Dictionary<string, WriteToPLC_Flag> s3PLCWriteData = new Dictionary<string, WriteToPLC_Flag>();
  1736. /// <summary>
  1737. /// [S3] 值板机
  1738. /// </summary>
  1739. /// <param name="plcNo">PLC编号</param>
  1740. //private void ReadStation_S3(int plcNo)
  1741. //{
  1742. // string stationCode = "[S3]";
  1743. // string stationName = "点散热胶装备";
  1744. // string stationNameStr = stationCode + stationName;
  1745. // string tagBaseName = "g_OP30_MES"; //标签变量名称
  1746. // string tagMesCommName = "mesCommToPC"; //标签变量名称
  1747. // string tagAgvCommName = "agvCommFrmPC";
  1748. // string tagBarsetName = "BarcodeSet";
  1749. // OP30_MesData_t stPLC_MesData; //PLC的MES数据
  1750. // (int, string) result;
  1751. // #region 创建字典
  1752. // // 触发信号字典 赋值
  1753. // s3PLCSignal_Old.Add("c1PLC_FLAG_Check", 0); // PLC_FLAG 进站校验
  1754. // s3PLCSignal_Old.Add("c1PLC_FLAG_Unbind", 0); // PLC_FLAG 二穴载具解绑
  1755. // s3PLCSignal_Old.Add("c1PLC_FLAG_Bind", 0); // PLC_FLAG 二穴载具绑定
  1756. // s3PLCSignal_Old.Add("c1PLC_FLAG", 0); // PLC_FLAG 出站接口
  1757. // s3PLCSignal_Old.Add("c1OEEPLC_FLAG", 0); // PLC_FLAG 节拍接口
  1758. // // PLC数据字典 赋值
  1759. // s3PLCData.Add("c1PLC_FLAG_Check", 0); // PLC_FLAG 进站校验
  1760. // s3PLCData.Add("c1MES_FLAG_Check", 0); // MES_FLAG
  1761. // s3PLCData.Add("c1ProductSN_Check", ""); // 产品SN(二穴载具SN)
  1762. // s3PLCData.Add("c1PLC_FLAG_Unbind", 0); // PLC_FLAG 二穴载具解绑
  1763. // s3PLCData.Add("c1MES_FLAG_Unbind", 0); // MES_FLAG
  1764. // //s3PLCData.Add("c1ProductSN_Check", ""); // 产品SN(二穴载具SN)
  1765. // s3PLCData.Add("c1VehicleCavity_Unbind", 0); // 二穴载具穴位号(产品取自二穴载具哪个穴位)
  1766. // s3PLCData.Add("c1PLC_FLAG_Bind", 0); // PLC_FLAG 二穴载具绑定
  1767. // s3PLCData.Add("c1MES_FLAG_Bind", 0); // MES_FLAG
  1768. // //s3PLCData.Add("c1ProductSN_Check", ""); // 产品SN(二穴载具SN)
  1769. // s3PLCData.Add("c1CavityReverse_Bind", 0); // 是否是两个穴位交换
  1770. // s3PLCData.Add("c1VehicleCavityFr_Bind", 0); // 来源穴位号(产品取自二穴载具哪个穴位)
  1771. // s3PLCData.Add("c1VehicleCavityTo_Bind", 0); // 目标载具穴位号(产品放到二穴载具哪个穴位)
  1772. // s3PLCData.Add("c1PLC_FLAG", 0); // PLC_FLAG 出站接口
  1773. // s3PLCData.Add("c1MES_FLAG", 0); // MES_FLAG
  1774. // s3PLCData.Add("c1ProductSN", ""); // 产品SN(一穴载具SN)
  1775. // //s3PLCData.Add("c1ProductSN_Check", ""); // 二穴载具SN(产品取自哪个二穴载具)
  1776. // s3PLCData.Add("c1VehicleCavity", 0); // 二穴载具穴位号(产品取自二穴载具哪个穴位)
  1777. // s3PLCData.Add("c1Result", 0); // 产品结果
  1778. // s3PLCData.Add("c1OEEPLC_FLAG", 0); // PLC_FLAG 节拍接口
  1779. // s3PLCData.Add("c1OEEMES_FLAG", 0); // MES_FLAG
  1780. // s3PLCData.Add("c1OEEProductSN", "");// 产品SN(载具SN)
  1781. // s3PLCData.Add("c1OEEType", 0); // 节拍类型(plc写入)
  1782. // #endregion 创建字典
  1783. // while (true)
  1784. // {
  1785. // try
  1786. // {
  1787. // if (!GlobalContext._IsCon_Funs2)
  1788. // {
  1789. // UpdatePLCMonitor(1, plcNo, 0);
  1790. // continue;
  1791. // }
  1792. // if (Funs[plcNo].IsConnected) // 检查PLC是否已连接上
  1793. // {
  1794. // Stopwatch stopwatch1 = new Stopwatch();
  1795. // Stopwatch stopwatch2 = new Stopwatch();
  1796. // stopwatch1.Start();
  1797. // stopwatch2.Start();
  1798. // #region 一次性读取所有数据
  1799. // // 一次性读取所有数据
  1800. // result = Funs[plcNo].Read_SingleTag<OP30_MesData_t>(tagBaseName, 1, out stPLC_MesData); //读取单个结构体数据
  1801. // if (result.Item1 != 0)
  1802. // {
  1803. // //richTextBox1.AppendText("\n" + strRet);
  1804. // }
  1805. // else
  1806. // {
  1807. // //richTextBox1.AppendText("\n" + "读取成功");
  1808. // }
  1809. // #endregion 一次性读取所有数据
  1810. // stopwatch2.Stop();
  1811. // #region 回写操作,写后清空flag
  1812. // mesCommToPC WriteBackToPLC = new mesCommToPC();
  1813. // result = Funs[plcNo].Write_SingleTag<mesCommToPC>(tagBaseName + "." + tagMesCommName, 1, WriteBackToPLC); //写入单个结构体数据
  1814. // #endregion 回写操作,写后清空flag
  1815. // #region 左边进站
  1816. // try
  1817. // {
  1818. // if (stPLC_MesData.mesCommFrmPLC.cmd == (byte)eMesCmd.InStation && !string.IsNullOrEmpty(stPLC_MesData.iotData.Left.work_type.ToString()))
  1819. // {
  1820. // Task.Run(() => S3进站(plcNo, stationNameStr, stPLC_MesData, tagBaseName + "." + tagMesCommName, tagBaseName + "." + tagBarsetName));
  1821. // //进站
  1822. // }
  1823. // }
  1824. // catch (Exception ex)
  1825. // {
  1826. // //Funs[plcNo].WriteMultipleRegisters<short>(2003, (short)6); // 6代表上位机报警
  1827. // string str = ex.StackTrace;
  1828. // AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 进站校验出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  1829. // }
  1830. // #endregion 进站
  1831. // #region 左边出站
  1832. // try
  1833. // {
  1834. // if (stPLC_MesData.mesCommFrmPLC.cmd == (byte)eMesCmd.OutStation)
  1835. // {
  1836. // Task.Run(() => S3出站(plcNo, stationNameStr, stPLC_MesData, tagBaseName + "." + tagMesCommName,"Left"));
  1837. // }
  1838. // }
  1839. // catch (Exception ex)
  1840. // {
  1841. // string str = ex.StackTrace;
  1842. // AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 上料进站出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  1843. // }
  1844. // #endregion 出站
  1845. // UpdatePLCMonitor(1, plcNo, 1); // 更新PLC状态的UI // 更新PLC状态的UI
  1846. // stopwatch1.Stop();
  1847. // //if (stopwatch1.ElapsedMilliseconds > 60) // ZS 稳定后取消注释该项
  1848. // OnMessage(LogType.Info, $"循环读取PLC数据一次,总用时{stopwatch1.ElapsedMilliseconds}ms[读取用时{stopwatch2.ElapsedMilliseconds}ms]");
  1849. // }
  1850. // else
  1851. // {
  1852. // UpdatePLCMonitor(1, plcNo, 0); // 更新PLC状态的UI
  1853. // AddMessage_Station(stationNameStr, LogType.Info, "PLC" + plcNo.ToString() + "_" + stationNameStr + "连接失败!");
  1854. // Funs[plcNo].Connect();
  1855. // }
  1856. // }
  1857. // catch (Exception ex)
  1858. // {
  1859. // UpdatePLCMonitor(1, plcNo, 0); // 更新PLC状态的UI
  1860. // AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr}运行出错!错误信息:" + ex.Message.ToString());
  1861. // //Funs[plcNo].ReConnect();
  1862. // }
  1863. // Thread.Sleep(IntervalReadPLC);
  1864. // }
  1865. //}
  1866. /// <summary>
  1867. /// [S3] 点散热胶装备
  1868. /// </summary>
  1869. /// <param name="plcNo">PLC编号</param>
  1870. /// <param name="stationNameStr">工站全称</param>
  1871. private void S3进站(int plcNo, string stationNameStr, OP30_MesData_t stPLC_MesData, string tagMesCommName, string tagBarsetName)
  1872. {
  1873. Stopwatch stopwatch1 = new Stopwatch();
  1874. Stopwatch stopwatch2 = new Stopwatch();
  1875. try
  1876. {
  1877. stopwatch1.Start();
  1878. string sn = "";//(string)stPLC_MesDataBarcodeSet.strProductBarcode; // 产品SN(物料码)
  1879. sn = sn.Replace("\0", "");
  1880. string strCarrierBarcode = "";//(string)stPLC_MesData.BarcodeSet.strCarrierBarcode; // 产品SN(物料码)
  1881. strCarrierBarcode = strCarrierBarcode.Replace("\0", "");
  1882. //载具码验证产品码
  1883. string strProductBarcode = SQLHelper.GetProductBarcodeByCarrierCode(strCarrierBarcode);
  1884. if (string.IsNullOrEmpty(strProductBarcode))
  1885. {
  1886. AddMessage_Station(stationNameStr, LogType.Error, $"PLC S3 点散热胶装备未能成功绑定载具信息");
  1887. }
  1888. if (!string.IsNullOrEmpty(strProductBarcode) && !string.IsNullOrEmpty(sn) && strProductBarcode != sn)
  1889. {
  1890. AddMessage_Station(stationNameStr, LogType.Error, $"PLC S3 点散热胶装备未能成功绑定载具信息");
  1891. }
  1892. // 产品SN(物料码)校验
  1893. List<TestItem> item = new List<TestItem>();
  1894. stopwatch2.Start();
  1895. int result = SaveStationInData(stationNameStr, GlobalContext.WorkOrderCode, GlobalContext.Mtltmrk, sn, item);
  1896. stopwatch2.Stop();
  1897. //指令执行结果 1:OK 110:失败
  1898. byte cmdToPC = (byte)(result == 1 ? 1 : 110);
  1899. //进站结果写入PLC
  1900. mesCommToPC MesToPLC = new mesCommToPC();
  1901. MesToPLC.cmd = cmdToPC;
  1902. MesToPLC.cmdParam = 0; //指令参数
  1903. MesToPLC.cmdResult = 1;
  1904. Funs[plcNo].Write_SingleTag<mesCommToPC>(tagMesCommName, 1, MesToPLC);
  1905. if (string.IsNullOrEmpty(sn))
  1906. {
  1907. BarcodeSet_t BarcodeToPlc = new BarcodeSet_t();
  1908. BarcodeToPlc.strCarrierBarcode = strCarrierBarcode;
  1909. BarcodeToPlc.strProductBarcode = sn;
  1910. Funs[plcNo].Write_SingleTag<BarcodeSet_t>(tagBarsetName, 1, BarcodeToPlc);
  1911. }
  1912. }
  1913. catch (Exception ex)
  1914. {
  1915. string str = ex.StackTrace;
  1916. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 上料进站校验出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  1917. mesCommToPC MesToPLC = new mesCommToPC();
  1918. MesToPLC.cmd = 0;
  1919. MesToPLC.cmdParam = 0; //指令参数
  1920. MesToPLC.cmdResult = 110;
  1921. Funs[plcNo].Write_SingleTag<mesCommToPC>(tagMesCommName, 1, MesToPLC);
  1922. }
  1923. stopwatch1.Stop();
  1924. AddMessage(LogType.Info, stationNameStr + "_进站;总用时" + stopwatch1.ElapsedMilliseconds + "ms;调用MES用时" + stopwatch2.ElapsedMilliseconds + "ms");
  1925. }
  1926. /// <summary>
  1927. /// [S3] 点散热胶装备 - 出站接口
  1928. /// </summary>
  1929. private void S3出站(int plcNo, string stationNameStr, OP30_MesData_t stPLC_MesData, string tagMesCommName,string direction)
  1930. {
  1931. Stopwatch stopwatch1 = new Stopwatch();
  1932. Stopwatch stopwatch2 = new Stopwatch();
  1933. try
  1934. {
  1935. stopwatch1.Start();
  1936. string workorder_code = GlobalContext.WorkOrderCode; // 工单号
  1937. string batch_num = GlobalContext.BatchNumber; // 批次号
  1938. string mtltmrk = (string)stPLC_MesData.BarcodeSet.strProductBarcode; // 产品条码; // 产品型号
  1939. mtltmrk = mtltmrk.Replace("\0", "");
  1940. string CarrierBarcode = (string)stPLC_MesData.BarcodeSet.strCarrierBarcode; // 载具条码;
  1941. CarrierBarcode = CarrierBarcode.Replace("\0", "");
  1942. // 产品结果
  1943. int a1Result = 0;
  1944. if (direction=="Left")
  1945. {
  1946. a1Result=(int)stPLC_MesData.iotData.Left.testStatus;
  1947. }
  1948. if (direction == "Right")
  1949. {
  1950. a1Result = (int)stPLC_MesData.iotData.Left.testStatus;
  1951. }
  1952. bool pass = a1Result == 1;
  1953. List<TestItem> items = new List<TestItem>();
  1954. items.Add(new TestItem()
  1955. {
  1956. Parameter_name = "载具码",
  1957. Parameter_value = CarrierBarcode,
  1958. Parameter_unit = ""
  1959. });
  1960. items.Add(new TestItem()
  1961. {
  1962. Parameter_name = "产品码",
  1963. Parameter_value = mtltmrk,
  1964. Parameter_unit = ""
  1965. });
  1966. //保存PLC返回MES数据到本地
  1967. int result1 = SwitctProcessData(stationNameStr, items, "", ""
  1968. , workorder_code, batch_num, mtltmrk, "", "", "", pass, CarrierBarcode, "1");
  1969. byte cmdToPC = (byte)(result1 == 1 ? 1 : 110);
  1970. stopwatch2.Start();
  1971. //进站结果写入PLC
  1972. mesCommToPC MesToPLC = new mesCommToPC();
  1973. MesToPLC.cmd = cmdToPC;
  1974. MesToPLC.cmdParam = 0; //指令参数
  1975. MesToPLC.cmdResult = 1;
  1976. Funs[plcNo].Write_SingleTag<mesCommToPC>(tagMesCommName, 1, MesToPLC);
  1977. stopwatch2.Stop();
  1978. WritePLCLog(LogType.Debug, $"PLC{plcNo}_[{stationNameStr}]-Write" + (result1 == 1 ? "成功!" : "失败!"));
  1979. }
  1980. catch (Exception ex)
  1981. {
  1982. stopwatch2.Start();
  1983. mesCommToPC MesToPLC = new mesCommToPC();
  1984. MesToPLC.cmd = 0;
  1985. MesToPLC.cmdParam = 0; //指令参数
  1986. MesToPLC.cmdResult = 110;
  1987. Funs[plcNo].Write_SingleTag<mesCommToPC>(tagMesCommName, 1, MesToPLC);
  1988. stopwatch2.Stop();
  1989. string str = ex.StackTrace;
  1990. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_[{stationNameStr}]上传加工报错!错误信息:" + ex.Message.ToString() + ";异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  1991. }
  1992. stopwatch1.Stop();
  1993. AddMessage(LogType.Info, stationNameStr + "_出站接口;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  1994. }
  1995. //// 上次采集到的SN
  1996. //private string sn_值板机 = string.Empty;
  1997. /// <summary>
  1998. /// [S3] 值板机 - 出站接口
  1999. /// </summary>
  2000. /// <param name="plcNo">PLC编号</param>
  2001. private void S3出站接口(int plcNo, string stationCode, string stationName)
  2002. {
  2003. Stopwatch stopwatch1 = new Stopwatch();
  2004. Stopwatch stopwatch2 = new Stopwatch();
  2005. string equipmentCode = GlobalContext.LineCode + "-" + stationCode; // 设备编号
  2006. string stationNameStr = stationCode + stationName;
  2007. string processItem = stationName; // 测试项目
  2008. try
  2009. {
  2010. stopwatch1.Start();
  2011. string workorder_code = GlobalContext.WorkOrderCode; // 工单号
  2012. string batch_num = GlobalContext.BatchNumber; // 批次号
  2013. string mtltmrk = GlobalContext.Mtltmrk; // 产品型号
  2014. string plcDate_YMD = DateTime.Now.ToString("yyyyMMdd");
  2015. string supplierCode = ""; // 供应商代码
  2016. string sn = (string)s3PLCData["c1ProductSN"]; // 产品SN(一穴载具SN)
  2017. sn = sn.Replace("\0", "");
  2018. string c1ProductSN_Check = (string)s3PLCData["c1ProductSN_Check"]; // 二穴载具SN(产品取自哪个二穴载具)
  2019. c1ProductSN_Check = c1ProductSN_Check.Replace("\0", "");
  2020. int c1VehicleCavity = (int)s3PLCData["c1VehicleCavity"]; // 二穴载具穴位号(产品取自二穴载具哪个穴位)
  2021. int c1Result = (int)s3PLCData["c1Result"]; // 产品结果
  2022. bool pass = c1Result == 1;
  2023. //
  2024. string productSN = string.Empty;
  2025. // 是否是两个穴位交换
  2026. List<TestItem> items = new List<TestItem>();
  2027. items.Add(new TestItem()
  2028. {
  2029. Parameter_name = "产品结果",
  2030. Parameter_value = c1Result == 1 ? "OK" : "NG",
  2031. Parameter_unit = ""
  2032. });
  2033. int result1 = SwitctProcessData(stationNameStr, items, equipmentCode, processItem
  2034. , workorder_code, batch_num, mtltmrk, plcDate_YMD, supplierCode, productSN, pass, sn, "1");
  2035. short result = result1 == 1 ? (short)1 : (short)2;
  2036. stopwatch2.Start();
  2037. // MES_Flag 为MES报错
  2038. // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  2039. //Funs[plcNo].WriteMultipleRegisters<short>(2150, result); // 4代表上位机报警
  2040. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  2041. writeToPLC_Flag.Name = "c1MES_FLAG";
  2042. writeToPLC_Flag.Adress = 2150;
  2043. writeToPLC_Flag.Value = result;
  2044. SxPLCWriteData_Add(ref s3PLCWriteData, "c1MES_FLAG", writeToPLC_Flag);
  2045. stopwatch2.Stop();
  2046. WritePLCLog(LogType.Debug, $"PLC{plcNo}_[{equipmentCode}]{processItem}-Write" + (result == 1 ? "成功!" : "失败!"));
  2047. }
  2048. catch (Exception ex)
  2049. {
  2050. stopwatch2.Start();
  2051. // MES_Flag 为4上位机报错
  2052. //Funs[plcNo].WriteMultipleRegisters<short>(2150, (short)4); // 4代表上位机报警
  2053. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  2054. writeToPLC_Flag.Name = "c1MES_FLAG";
  2055. writeToPLC_Flag.Adress = 2150;
  2056. writeToPLC_Flag.Value = (short)4;
  2057. SxPLCWriteData_Add(ref s3PLCWriteData, "c1MES_FLAG", writeToPLC_Flag);
  2058. stopwatch2.Stop();
  2059. string str = ex.StackTrace;
  2060. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_[{equipmentCode}]{processItem}上传出站接口报错!错误信息:" + ex.Message.ToString() + ";异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  2061. }
  2062. stopwatch1.Stop();
  2063. AddMessage(LogType.Info, stationNameStr + "_出站接口;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  2064. }
  2065. /// <summary>
  2066. /// [S3] 值板机- 节拍接口
  2067. /// </summary>
  2068. /// <param name="plcNo">PLC编号</param>
  2069. /// <param name="stationNameStr">工站全称</param>
  2070. private void S3节拍接口(int plcNo, string stationNameStr)
  2071. {
  2072. Stopwatch stopwatch1 = new Stopwatch();
  2073. Stopwatch stopwatch2 = new Stopwatch();
  2074. string resultStr = string.Empty;
  2075. try
  2076. {
  2077. stopwatch1.Start();
  2078. string oEEType = ((int)s3PLCData["c1OEEType"]).ToString(); // 节拍类型(plc写入)
  2079. string c1OEEProductSN = (string)s3PLCData["c1OEEProductSN"]; // 载具SN
  2080. c1OEEProductSN = c1OEEProductSN.Replace("\0", "");
  2081. bool actionBool = Enum.TryParse(oEEType, out XiaomiDeviceOEE deviceOEE);
  2082. if (!actionBool)
  2083. {
  2084. stopwatch2.Start();
  2085. // MES_Flag
  2086. //Funs[plcNo].WriteMultipleRegisters<short>(2204, (short)4); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  2087. WriteToPLC_Flag writeToPLC_Flag1 = new WriteToPLC_Flag(); // MES_Flag
  2088. writeToPLC_Flag1.Name = "c1OEEMES_FLAG";
  2089. writeToPLC_Flag1.Adress = 2204;
  2090. writeToPLC_Flag1.Value = (short)4;
  2091. SxPLCWriteData_Add(ref s3PLCWriteData, "c1OEEMES_FLAG", writeToPLC_Flag1);
  2092. stopwatch2.Stop();
  2093. AddMessage(LogType.Info, stationNameStr + $"_节拍接口-- 设备上传了未识别的节拍类型【{oEEType}】请检查;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  2094. return;
  2095. }
  2096. string c1OEEPartNo = string.Empty; // 物料码
  2097. if (string.IsNullOrEmpty(c1OEEProductSN))
  2098. {
  2099. stopwatch2.Start();
  2100. // MES_Flag
  2101. //Funs[plcNo].WriteMultipleRegisters<short>(2204, (short)1); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  2102. WriteToPLC_Flag writeToPLC_Flag1 = new WriteToPLC_Flag(); // MES_Flag
  2103. writeToPLC_Flag1.Name = "c1OEEMES_FLAG";
  2104. writeToPLC_Flag1.Adress = 2204;
  2105. writeToPLC_Flag1.Value = (short)1;
  2106. SxPLCWriteData_Add(ref s3PLCWriteData, "c1OEEMES_FLAG", writeToPLC_Flag1);
  2107. stopwatch2.Stop();
  2108. AddMessage(LogType.Info, stationNameStr + $"_节拍接口-- 上传内容无效已自动省略;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  2109. return;
  2110. }
  2111. else
  2112. { // 查产品SN
  2113. c1OEEPartNo = "Test"; // ZS
  2114. }
  2115. short c1OEEMES_FLAG = 0;
  2116. // 上传OEE
  2117. (short, string) result = SaveOEEData(plcNo, stationNameStr, deviceOEE, c1OEEPartNo, c1OEEProductSN);
  2118. c1OEEMES_FLAG = result.Item1;
  2119. resultStr = result.Item2;
  2120. stopwatch2.Start();
  2121. // MES_Flag
  2122. //Funs[plcNo].WriteMultipleRegisters<short>(2204, c1OEEMES_FLAG); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  2123. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  2124. writeToPLC_Flag.Name = "c1OEEMES_FLAG";
  2125. writeToPLC_Flag.Adress = 2204;
  2126. writeToPLC_Flag.Value = c1OEEMES_FLAG;
  2127. SxPLCWriteData_Add(ref s3PLCWriteData, "c1OEEMES_FLAG", writeToPLC_Flag);
  2128. stopwatch2.Stop();
  2129. }
  2130. catch (Exception ex)
  2131. {
  2132. string str = ex.StackTrace;
  2133. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 节拍接口出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  2134. // MES_Flag
  2135. stopwatch2.Start();
  2136. //Funs[plcNo].WriteMultipleRegisters<short>(2204, (short)4); // 4代表上位机报警
  2137. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  2138. writeToPLC_Flag.Name = "c1OEEMES_FLAG";
  2139. writeToPLC_Flag.Adress = 2204;
  2140. writeToPLC_Flag.Value = (short)4;
  2141. SxPLCWriteData_Add(ref s3PLCWriteData, "c1OEEMES_FLAG", writeToPLC_Flag);
  2142. stopwatch2.Stop();
  2143. }
  2144. stopwatch1.Stop();
  2145. AddMessage(LogType.Info, stationNameStr + $"_节拍接口-- {resultStr};总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  2146. }
  2147. #endregion [S3] 值板机
  2148. #endregion PLC3 刘永村
  2149. #region PLC4 刘果段
  2150. #region [S4] 取放桁架
  2151. /// <summary>
  2152. /// S4工位的数据- 触发信号上次的值
  2153. /// </summary>
  2154. private Dictionary<string, object> s4PLCSignal_Old = new Dictionary<string, object>();
  2155. /// <summary>
  2156. /// S4工位的数据(含触发信号)
  2157. /// </summary>
  2158. private Dictionary<string, object> s4PLCData = new Dictionary<string, object>();
  2159. /// <summary>
  2160. /// S4工位的数据- 回写点位
  2161. /// </summary>
  2162. private Dictionary<string, WriteToPLC_Flag> s4PLCWriteData = new Dictionary<string, WriteToPLC_Flag>();
  2163. /// <summary>
  2164. /// [S4] 取放桁架
  2165. /// </summary>
  2166. /// <param name="plcNo">PLC编号</param>
  2167. private void ReadStation_S4(int plcNo)
  2168. {
  2169. // [S1] Tray盘上料装备
  2170. // [S2] FCT
  2171. // [S3] 值板机
  2172. // [S4_1] 载具下线装备 [S4_5] 载具上线装备
  2173. // [S5] Tray盘下料装备
  2174. /// 上位机心跳
  2175. /// 获取设备报警数据与状态信息
  2176. string stationCode = "[S4_1]";
  2177. string stationName = "载具下线装备";
  2178. string stationNameStr = stationCode + stationName;
  2179. string stationCode5 = "[S4_5]";
  2180. string stationName5 = "载具上线装备";
  2181. string stationNameStr5 = stationCode5 + stationName5;
  2182. #region 创建字典
  2183. // 触发信号字典 赋值
  2184. s4PLCSignal_Old.Add("d1BulletclipScanCode", 0); // 扫码信号 弹夹扫码
  2185. s4PLCSignal_Old.Add("d1VehicleScanCode", 0); // 扫码信号 载具扫码
  2186. s4PLCSignal_Old.Add("d1PLC_FLAG", 0); // PLC_FLAG 出站接口
  2187. s4PLCSignal_Old.Add("d1OEEPLC_FLAG", 0); // PLC_FLAG 节拍接口
  2188. s4PLCSignal_Old.Add("d2BulletclipScanCode", 0); // 扫码信号 查询标机中弹夹的状态
  2189. s4PLCSignal_Old.Add("d3PLC_FLAG", 0); // PLC_FLAG 真空标机1出站接口
  2190. s4PLCSignal_Old.Add("d4PLC_FLAG", 0); // PLC_FLAG 真空标机2出站接口
  2191. s4PLCSignal_Old.Add("d5BulletclipScanCode", 0); // 扫码信号 弹夹扫码
  2192. s4PLCSignal_Old.Add("d5VehicleScanCode", 0); // 扫码信号 载具扫码
  2193. s4PLCSignal_Old.Add("d5PLC_FLAG", 0); // PLC_FLAG 出站接口
  2194. s4PLCSignal_Old.Add("d5OEEPLC_FLAG", 0); // PLC_FLAG 节拍接口
  2195. // PLC数据字典 赋值
  2196. // 载具下线装备(弹夹上线)
  2197. s4PLCData.Add("d1BulletclipScanCode", 0); // 扫码信号 弹夹扫码
  2198. s4PLCData.Add("d1BulletclipCode", ""); // 扫到的码
  2199. s4PLCData.Add("d1VehicleScanCode", 0); // 扫码信号 载具扫码
  2200. s4PLCData.Add("d1VehicleCode", ""); // 扫到的码
  2201. s4PLCData.Add("d1PLC_FLAG", 0); // PLC_FLAG 出站接口
  2202. s4PLCData.Add("d1MES_FLAG", 0); // MES_FLAG
  2203. s4PLCData.Add("d1ProductSN", ""); // 产品SN(弹夹码)
  2204. s4PLCData.Add("d1VehicleCode1", ""); // 载具1码(弹夹穴位1)
  2205. s4PLCData.Add("d1VehicleCode2", ""); // 载具2码(弹夹穴位2)
  2206. s4PLCData.Add("d1VehicleCode3", ""); // 载具3码(弹夹穴位3)
  2207. s4PLCData.Add("d1VehicleCode4", ""); // 载具4码(弹夹穴位4)
  2208. s4PLCData.Add("d1VehicleCode5", ""); // 载具5码(弹夹穴位5)
  2209. s4PLCData.Add("d1VehicleCode6", ""); // 载具6码(弹夹穴位6)
  2210. s4PLCData.Add("d1VehicleCode7", ""); // 载具7码(弹夹穴位7)
  2211. s4PLCData.Add("d1VehicleCode8", ""); // 载具8码(弹夹穴位8)
  2212. s4PLCData.Add("d1VehicleCode9", ""); // 载具9码(弹夹穴位9)
  2213. s4PLCData.Add("d1VehicleCode10", ""); // 载具10码(弹夹穴位10)
  2214. s4PLCData.Add("d1Result", 0); // 产品结果
  2215. s4PLCData.Add("d1OEEPLC_FLAG", 0); // PLC_FLAG 节拍接口
  2216. s4PLCData.Add("d1OEEMES_FLAG", 0); // MES_FLAG
  2217. s4PLCData.Add("d1OEEProductSN", "");// 产品SN(载具SN)
  2218. s4PLCData.Add("d1OEEType", 0); // 节拍类型(plc写入)
  2219. s4PLCData.Add("d2BulletclipScanCode", 0); // 扫码信号 查询标机中弹夹的状态
  2220. s4PLCData.Add("d2BulletclipStates", 0); // 弹夹状态
  2221. s4PLCData.Add("d2BulletclipCode", ""); // 扫到的码
  2222. // 真空标机(提升机)
  2223. s4PLCData.Add("d3PLC_FLAG", 0); // PLC_FLAG 真空标机1出站接口
  2224. s4PLCData.Add("d3MES_FLAG", 0); // MES_FLAG
  2225. s4PLCData.Add("d3Type", 0); // 进站还是出站
  2226. s4PLCData.Add("d3ProductSN", ""); // 产品SN(弹夹码)
  2227. s4PLCData.Add("d3Result", 0); // 产品结果
  2228. s4PLCData.Add("d4PLC_FLAG", 0); // PLC_FLAG 真空标机2出站接口
  2229. s4PLCData.Add("d4MES_FLAG", 0); // MES_FLAG
  2230. s4PLCData.Add("d4Type", 0); // 进站还是出站
  2231. s4PLCData.Add("d4ProductSN", ""); // 产品SN(弹夹码)
  2232. s4PLCData.Add("d4Result", 0); // 产品结果
  2233. // 载具上线装备(弹夹下线)
  2234. s4PLCData.Add("d5BulletclipScanCode", 0); // 扫码信号 弹夹扫码
  2235. s4PLCData.Add("d5BulletclipCode", ""); // 扫到的码
  2236. s4PLCData.Add("d5VehicleScanCode", 0); // 扫码信号 载具扫码
  2237. s4PLCData.Add("d5VehicleCode", ""); // 扫到的码
  2238. s4PLCData.Add("d5PLC_FLAG", 0); // PLC_FLAG 出站接口
  2239. s4PLCData.Add("d5MES_FLAG", 0); // MES_FLAG
  2240. s4PLCData.Add("d5ProductSN", ""); // 产品SN(弹夹码)
  2241. s4PLCData.Add("d5VehicleCode1", ""); // 载具1码(弹夹穴位1)
  2242. s4PLCData.Add("d5VehicleCode2", ""); // 载具2码(弹夹穴位2)
  2243. s4PLCData.Add("d5VehicleCode3", ""); // 载具3码(弹夹穴位3)
  2244. s4PLCData.Add("d5VehicleCode4", ""); // 载具4码(弹夹穴位4)
  2245. s4PLCData.Add("d5VehicleCode5", ""); // 载具5码(弹夹穴位5)
  2246. s4PLCData.Add("d5VehicleCode6", ""); // 载具6码(弹夹穴位6)
  2247. s4PLCData.Add("d5VehicleCode7", ""); // 载具7码(弹夹穴位7)
  2248. s4PLCData.Add("d5VehicleCode8", ""); // 载具8码(弹夹穴位8)
  2249. s4PLCData.Add("d5VehicleCode9", ""); // 载具9码(弹夹穴位9)
  2250. s4PLCData.Add("d5VehicleCode10", ""); // 载具10码(弹夹穴位10)
  2251. s4PLCData.Add("d5Result", 0); // 产品结果
  2252. s4PLCData.Add("d5OEEPLC_FLAG", 0); // PLC_FLAG 节拍接口
  2253. s4PLCData.Add("d5OEEMES_FLAG", 0); // MES_FLAG
  2254. s4PLCData.Add("d5OEEProductSN", "");// 产品SN(载具SN)
  2255. s4PLCData.Add("d5OEEType", 0); // 节拍类型(plc写入)
  2256. #endregion 创建字典
  2257. while (true)
  2258. {
  2259. try
  2260. {
  2261. if (!GlobalContext._IsCon_Funs4)
  2262. {
  2263. UpdatePLCMonitor(1, plcNo, 0);
  2264. continue;
  2265. }
  2266. if (Funs[plcNo].IsConnected) // 检查PLC是否已连接上
  2267. {
  2268. Stopwatch stopwatch1 = new Stopwatch();
  2269. Stopwatch stopwatch2 = new Stopwatch();
  2270. stopwatch1.Start();
  2271. stopwatch2.Start();
  2272. /*
  2273. #region 一次性读取所有数据
  2274. // 载具下线装备(弹夹上线)
  2275. int[] data1 = Funs[plcNo].ReadHoldingRegisters(2000, 100);
  2276. int[] data2 = Funs[plcNo].ReadHoldingRegisters(2100, 100);
  2277. int[] data3 = Funs[plcNo].ReadHoldingRegisters(2200, 100);
  2278. int[] data4 = Funs[plcNo].ReadHoldingRegisters(2300, 100);
  2279. int[] data5 = Funs[plcNo].ReadHoldingRegisters(2400, 100);
  2280. int[] data6 = Funs[plcNo].ReadHoldingRegisters(2500, 100);
  2281. int[] data7 = Funs[plcNo].ReadHoldingRegisters(2600, 100);
  2282. int[] data8 = Funs[plcNo].ReadHoldingRegisters(2700, 100);
  2283. int[] data9 = Funs[plcNo].ReadHoldingRegisters(2800, 100);
  2284. int[] data10 = Funs[plcNo].ReadHoldingRegisters(2900, 56);
  2285. int[] datas = data1.Concat(data2).ToArray();
  2286. datas = datas.Concat(data3).ToArray();
  2287. datas = datas.Concat(data4).ToArray();
  2288. datas = datas.Concat(data5).ToArray();
  2289. datas = datas.Concat(data6).ToArray();
  2290. datas = datas.Concat(data7).ToArray();
  2291. datas = datas.Concat(data8).ToArray();
  2292. datas = datas.Concat(data9).ToArray();
  2293. datas = datas.Concat(data10).ToArray();
  2294. // 载具下线装备(弹夹上线)
  2295. s4PLCData["d1BulletclipScanCode"] = datas[2]; // 扫码信号 弹夹扫码
  2296. int[] d1BulletclipCodeData = datas.Skip(3).Take(20).ToArray();
  2297. s4PLCData["d1BulletclipCode"] = ModbusClient.ConvertRegistersToString(d1BulletclipCodeData, 0, 40);
  2298. s4PLCData["d1VehicleScanCode"] = datas[33]; // 扫码信号 载具扫码
  2299. int[] d1VehicleCodeData = datas.Skip(34).Take(20).ToArray();
  2300. s4PLCData["d1VehicleCode"] = ModbusClient.ConvertRegistersToString(d1VehicleCodeData, 0, 40);
  2301. s4PLCData["d1PLC_FLAG"] = datas[64]; // PLC_FLAG 出站接口
  2302. s4PLCData["d1MES_FLAG"] = datas[65];
  2303. int[] d1ProductSNData = datas.Skip(66).Take(20).ToArray();
  2304. s4PLCData["d1ProductSN"] = ModbusClient.ConvertRegistersToString(d1ProductSNData, 0, 40); // 产品SN(物料码)
  2305. int[] d1VehicleCode1Data = datas.Skip(86).Take(20).ToArray();
  2306. s4PLCData["d1VehicleCode1"] = ModbusClient.ConvertRegistersToString(d1VehicleCode1Data, 0, 40);
  2307. int[] d1VehicleCode2Data = datas.Skip(106).Take(20).ToArray();
  2308. s4PLCData["d1VehicleCode2"] = ModbusClient.ConvertRegistersToString(d1VehicleCode2Data, 0, 40);
  2309. int[] d1VehicleCode3Data = datas.Skip(126).Take(20).ToArray();
  2310. s4PLCData["d1VehicleCode3"] = ModbusClient.ConvertRegistersToString(d1VehicleCode3Data, 0, 40);
  2311. int[] d1VehicleCode4Data = datas.Skip(146).Take(20).ToArray();
  2312. s4PLCData["d1VehicleCode4"] = ModbusClient.ConvertRegistersToString(d1VehicleCode4Data, 0, 40);
  2313. int[] d1VehicleCode5Data = datas.Skip(166).Take(20).ToArray();
  2314. s4PLCData["d1VehicleCode5"] = ModbusClient.ConvertRegistersToString(d1VehicleCode5Data, 0, 40);
  2315. int[] d1VehicleCode6Data = datas.Skip(186).Take(20).ToArray();
  2316. s4PLCData["d1VehicleCode6"] = ModbusClient.ConvertRegistersToString(d1VehicleCode6Data, 0, 40);
  2317. int[] d1VehicleCode7Data = datas.Skip(206).Take(20).ToArray();
  2318. s4PLCData["d1VehicleCode7"] = ModbusClient.ConvertRegistersToString(d1VehicleCode7Data, 0, 40);
  2319. int[] d1VehicleCode8Data = datas.Skip(226).Take(20).ToArray();
  2320. s4PLCData["d1VehicleCode8"] = ModbusClient.ConvertRegistersToString(d1VehicleCode8Data, 0, 40);
  2321. int[] d1VehicleCode9Data = datas.Skip(246).Take(20).ToArray();
  2322. s4PLCData["d1VehicleCode9"] = ModbusClient.ConvertRegistersToString(d1VehicleCode9Data, 0, 40);
  2323. int[] d1VehicleCode10Data = datas.Skip(266).Take(20).ToArray();
  2324. s4PLCData["d1VehicleCode10"] = ModbusClient.ConvertRegistersToString(d1VehicleCode10Data, 0, 40);
  2325. int[] d1VehicleCode11Data = datas.Skip(286).Take(20).ToArray();
  2326. s4PLCData["d1VehicleCode11"] = ModbusClient.ConvertRegistersToString(d1VehicleCode11Data, 0, 40);
  2327. int[] d1VehicleCode12Data = datas.Skip(306).Take(20).ToArray();
  2328. s4PLCData["d1VehicleCode12"] = ModbusClient.ConvertRegistersToString(d1VehicleCode12Data, 0, 40);
  2329. int[] d1VehicleCode13Data = datas.Skip(326).Take(20).ToArray();
  2330. s4PLCData["d1VehicleCode13"] = ModbusClient.ConvertRegistersToString(d1VehicleCode13Data, 0, 40);
  2331. int[] d1VehicleCode14Data = datas.Skip(346).Take(20).ToArray();
  2332. s4PLCData["d1VehicleCode14"] = ModbusClient.ConvertRegistersToString(d1VehicleCode14Data, 0, 40);
  2333. int[] d1VehicleCode15Data = datas.Skip(366).Take(20).ToArray();
  2334. s4PLCData["d1VehicleCode15"] = ModbusClient.ConvertRegistersToString(d1VehicleCode15Data, 0, 40);
  2335. s4PLCData["d1Result"] = datas[386];
  2336. s4PLCData["d1OEEPLC_FLAG"] = datas[397]; // PLC_FLAG 节拍接口
  2337. s4PLCData["d1OEEMES_FLAG"] = datas[398];
  2338. int[] d1OEEProductSNData = datas.Skip(399).Take(20).ToArray();
  2339. s4PLCData["d1OEEProductSN"] = ModbusClient.ConvertRegistersToString(d1OEEProductSNData, 0, 40);
  2340. s4PLCData["d1OEEType"] = datas[419];
  2341. // 桁架(查询标机中弹夹的状态)
  2342. s4PLCData["d2BulletclipScanCode"] = datas[430];
  2343. s4PLCData["d2BulletclipStates"] = datas[431];
  2344. int[] d2BulletclipCodeData = datas.Skip(432).Take(20).ToArray();
  2345. s4PLCData["d2BulletclipCode"] = ModbusClient.ConvertRegistersToString(d2BulletclipCodeData, 0, 40);
  2346. // 真空标机
  2347. s4PLCData["d3PLC_FLAG"] = datas[462]; // 真空标机1 出站接口
  2348. s4PLCData["d3MES_FLAG"] = datas[463];
  2349. int[] d3ProductSNData = datas.Skip(464).Take(20).ToArray();
  2350. s4PLCData["d3ProductSN"] = ModbusClient.ConvertRegistersToString(d3ProductSNData, 0, 40);
  2351. s4PLCData["d3Result"] = datas[484];
  2352. s4PLCData["d3Type"] = datas[485];
  2353. s4PLCData["d4PLC_FLAG"] = datas[495]; // 真空标机2 出站接口
  2354. s4PLCData["d4MES_FLAG"] = datas[496];
  2355. int[] d4ProductSNData = datas.Skip(497).Take(20).ToArray();
  2356. s4PLCData["d4ProductSN"] = ModbusClient.ConvertRegistersToString(d4ProductSNData, 0, 40);
  2357. s4PLCData["d4Result"] = datas[517];
  2358. s4PLCData["d4Type"] = datas[518];
  2359. // 载具上线装备(弹夹下线)
  2360. s4PLCData["d5BulletclipScanCode"] = datas[528]; // 扫码信号 弹夹扫码
  2361. int[] d5BulletclipCodeData = datas.Skip(529).Take(20).ToArray();
  2362. s4PLCData["d5BulletclipCode"] = ModbusClient.ConvertRegistersToString(d5BulletclipCodeData, 0, 40);
  2363. s4PLCData["d5VehicleScanCode"] = datas[559]; // 扫码信号 载具扫码
  2364. int[] d5VehicleCodeData = datas.Skip(560).Take(20).ToArray();
  2365. s4PLCData["d5VehicleCode"] = ModbusClient.ConvertRegistersToString(d5VehicleCodeData, 0, 40);
  2366. s4PLCData["d5PLC_FLAG"] = datas[590]; // PLC_FLAG 出站接口
  2367. s4PLCData["d5MES_FLAG"] = datas[591];
  2368. int[] d5ProductSNData = datas.Skip(592).Take(20).ToArray();
  2369. s4PLCData["d5ProductSN"] = ModbusClient.ConvertRegistersToString(d5ProductSNData, 0, 40); // 产品SN(物料码)
  2370. int[] d5VehicleCode1Data = datas.Skip(612).Take(20).ToArray();
  2371. s4PLCData["d5VehicleCode1"] = ModbusClient.ConvertRegistersToString(d5VehicleCode1Data, 0, 40);
  2372. int[] d5VehicleCode2Data = datas.Skip(632).Take(20).ToArray();
  2373. s4PLCData["d5VehicleCode2"] = ModbusClient.ConvertRegistersToString(d5VehicleCode2Data, 0, 40);
  2374. int[] d5VehicleCode3Data = datas.Skip(652).Take(20).ToArray();
  2375. s4PLCData["d5VehicleCode3"] = ModbusClient.ConvertRegistersToString(d5VehicleCode3Data, 0, 40);
  2376. int[] d5VehicleCode4Data = datas.Skip(672).Take(20).ToArray();
  2377. s4PLCData["d5VehicleCode4"] = ModbusClient.ConvertRegistersToString(d5VehicleCode4Data, 0, 40);
  2378. int[] d5VehicleCode5Data = datas.Skip(692).Take(20).ToArray();
  2379. s4PLCData["d5VehicleCode5"] = ModbusClient.ConvertRegistersToString(d5VehicleCode5Data, 0, 40);
  2380. int[] d5VehicleCode6Data = datas.Skip(712).Take(20).ToArray();
  2381. s4PLCData["d5VehicleCode6"] = ModbusClient.ConvertRegistersToString(d5VehicleCode6Data, 0, 40);
  2382. int[] d5VehicleCode7Data = datas.Skip(732).Take(20).ToArray();
  2383. s4PLCData["d5VehicleCode7"] = ModbusClient.ConvertRegistersToString(d5VehicleCode7Data, 0, 40);
  2384. int[] d5VehicleCode8Data = datas.Skip(752).Take(20).ToArray();
  2385. s4PLCData["d5VehicleCode8"] = ModbusClient.ConvertRegistersToString(d5VehicleCode8Data, 0, 40);
  2386. int[] d5VehicleCode9Data = datas.Skip(772).Take(20).ToArray();
  2387. s4PLCData["d5VehicleCode9"] = ModbusClient.ConvertRegistersToString(d5VehicleCode9Data, 0, 40);
  2388. int[] d5VehicleCode10Data = datas.Skip(792).Take(20).ToArray();
  2389. s4PLCData["d5VehicleCode10"] = ModbusClient.ConvertRegistersToString(d5VehicleCode10Data, 0, 40);
  2390. int[] d5VehicleCode11Data = datas.Skip(812).Take(20).ToArray();
  2391. s4PLCData["d5VehicleCode11"] = ModbusClient.ConvertRegistersToString(d5VehicleCode11Data, 0, 40);
  2392. int[] d5VehicleCode12Data = datas.Skip(832).Take(20).ToArray();
  2393. s4PLCData["d5VehicleCode12"] = ModbusClient.ConvertRegistersToString(d5VehicleCode12Data, 0, 40);
  2394. int[] d5VehicleCode13Data = datas.Skip(852).Take(20).ToArray();
  2395. s4PLCData["d5VehicleCode13"] = ModbusClient.ConvertRegistersToString(d5VehicleCode13Data, 0, 40);
  2396. int[] d5VehicleCode14Data = datas.Skip(872).Take(20).ToArray();
  2397. s4PLCData["d5VehicleCode14"] = ModbusClient.ConvertRegistersToString(d5VehicleCode14Data, 0, 40);
  2398. int[] d5VehicleCode15Data = datas.Skip(892).Take(20).ToArray();
  2399. s4PLCData["d5VehicleCode15"] = ModbusClient.ConvertRegistersToString(d5VehicleCode15Data, 0, 40);
  2400. s4PLCData["d5Result"] = datas[912];
  2401. s4PLCData["d5OEEPLC_FLAG"] = datas[923]; // PLC_FLAG 节拍接口
  2402. s4PLCData["d5OEEMES_FLAG"] = datas[924];
  2403. int[] d5OEEProductSNData = datas.Skip(925).Take(20).ToArray();
  2404. s4PLCData["d5OEEProductSN"] = ModbusClient.ConvertRegistersToString(d5OEEProductSNData, 0, 40);
  2405. s4PLCData["d5OEEType"] = datas[945];
  2406. #endregion 一次性读取所有数据
  2407. stopwatch2.Stop();
  2408. #region 回写操作,写后清空flag
  2409. PLCWriteData(Funs[plcNo], ref s4PLCData, ref s4PLCWriteData);
  2410. #endregion 回写操作,写后清空flag
  2411. */
  2412. // N801A-S4_1 弹夹扫码
  2413. #region N801A-S4_1 弹夹扫码
  2414. try
  2415. {
  2416. int d1BulletclipScanCode = (int)s4PLCData["d1BulletclipScanCode"];
  2417. int d1BulletclipScanCodeOld = (int)s4PLCSignal_Old["d1BulletclipScanCode"];
  2418. if (d1BulletclipScanCode != d1BulletclipScanCodeOld)
  2419. {
  2420. if (d1BulletclipScanCode == 1) // 0->1
  2421. Task.Run(() => S4_1弹夹扫码(plcNo, stationNameStr)); // MreTasks[1].Set();
  2422. s4PLCSignal_Old["d1BulletclipScanCode"] = s4PLCData["d1BulletclipScanCode"];
  2423. }
  2424. }
  2425. catch (Exception ex)
  2426. {
  2427. //Funs[plcNo].WriteMultipleRegisters<short>(2002, (short)6); // 6代表上位机报警
  2428. string str = ex.StackTrace;
  2429. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 弹夹扫码出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  2430. }
  2431. #endregion N801A-S4_1 弹夹扫码
  2432. // N801A-S4_1 载具扫码
  2433. #region N801A-S4_1 载具扫码
  2434. try
  2435. {
  2436. int d1VehicleScanCode = (int)s4PLCData["d1VehicleScanCode"];
  2437. int d1VehicleScanCodeOld = (int)s4PLCSignal_Old["d1VehicleScanCode"];
  2438. if (d1VehicleScanCode != d1VehicleScanCodeOld)
  2439. {
  2440. if (d1VehicleScanCode == 1) // 0->1
  2441. Task.Run(() => S4_1载具扫码(plcNo, stationNameStr)); // MreTasks[1].Set();
  2442. s4PLCSignal_Old["d1VehicleScanCode"] = s4PLCData["d1VehicleScanCode"];
  2443. }
  2444. }
  2445. catch (Exception ex)
  2446. {
  2447. //Funs[plcNo].WriteMultipleRegisters<short>(2033, (short)6); // 6代表上位机报警
  2448. string str = ex.StackTrace;
  2449. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 载具扫码出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  2450. }
  2451. #endregion N801A-S4_1 载具扫码
  2452. // N801A-S4_1 出站接口
  2453. #region N801A-S4_1 出站接口
  2454. try
  2455. {
  2456. int d1PLC_FLAG = (int)s4PLCData["d1PLC_FLAG"];
  2457. int d1MES_FLAG = (int)s4PLCData["d1MES_FLAG"];
  2458. int d1PLC_FLAGOld = (int)s4PLCSignal_Old["d1PLC_FLAG"];
  2459. if (d1PLC_FLAG != d1PLC_FLAGOld)
  2460. {
  2461. if (d1PLC_FLAG == 1 && d1MES_FLAG == 0) // 0->1
  2462. Task.Run(() => S4_1出站接口(plcNo, stationCode, stationName)); // MreTasks[3].Set();
  2463. //else if (d1PLC_FLAG == 0 && d1MES_FLAG != 0)
  2464. //Funs[plcNo].WriteMultipleRegisters<short>(2065, (short)0);
  2465. s4PLCSignal_Old["d1PLC_FLAG"] = s4PLCData["d1PLC_FLAG"];
  2466. }
  2467. }
  2468. catch (Exception ex)
  2469. {
  2470. //Funs[plcNo].WriteMultipleRegisters<short>(2065, (short)6); // 6代表上位机报警
  2471. string str = ex.StackTrace;
  2472. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 上传出站接口出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  2473. }
  2474. #endregion N801A-S4_1 出站接口
  2475. // N801A-S4_1 节拍接口
  2476. #region N801A-S4_1 节拍接口
  2477. try
  2478. {
  2479. int d1OEEPLC_FLAG = (int)s4PLCData["d1OEEPLC_FLAG"];
  2480. int d1OEEMES_FLAG = (int)s4PLCData["d1OEEMES_FLAG"];
  2481. int d1OEEPLC_FLAGOld = (int)s4PLCSignal_Old["d1OEEPLC_FLAG"];
  2482. if (d1OEEPLC_FLAG != d1OEEPLC_FLAGOld)
  2483. {
  2484. if (d1OEEPLC_FLAG == 1 && d1OEEMES_FLAG == 0) // 0->1
  2485. Task.Run(() => S4_1节拍接口(plcNo, stationNameStr)); // MreTasks[4].Set();
  2486. //else if (d1OEEPLC_FLAG == 0 && d1OEEMES_FLAG != 0)
  2487. //Funs[plcNo].WriteMultipleRegisters<short>(2398, (short)0);
  2488. s4PLCSignal_Old["d1OEEPLC_FLAG"] = s4PLCData["d1OEEPLC_FLAG"];
  2489. }
  2490. }
  2491. catch (Exception ex)
  2492. {
  2493. //Funs[plcNo].WriteMultipleRegisters<short>(2398, (short)4); // 4代表上位机报警
  2494. string str = ex.StackTrace;
  2495. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 上传节拍接口出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  2496. }
  2497. #endregion N801A-S4_1 节拍接口
  2498. // N801A-S4_2 桁架(查询标机中弹夹的状态) 数据
  2499. #region N801A-S4_2 桁架(查询标机中弹夹的状态)
  2500. try
  2501. {
  2502. int d2BulletclipScanCode = (int)s4PLCData["d2BulletclipScanCode"];
  2503. int d2BulletclipScanCodeOld = (int)s4PLCSignal_Old["d2BulletclipScanCode"];
  2504. if (d2BulletclipScanCode != d2BulletclipScanCodeOld)
  2505. {
  2506. if (d2BulletclipScanCode == 1) // 0->1
  2507. Task.Run(() => S4_2桁架(plcNo, stationNameStr)); // MreTasks[1].Set();
  2508. s4PLCSignal_Old["d2BulletclipScanCode"] = s4PLCData["d2BulletclipScanCode"];
  2509. }
  2510. }
  2511. catch (Exception ex)
  2512. {
  2513. //Funs[plcNo].WriteMultipleRegisters<short>(2430, (short)6); // 6代表上位机报警
  2514. string str = ex.StackTrace;
  2515. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 桁架出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  2516. }
  2517. #endregion N801A-S4_2 桁架(查询标机中弹夹的状态)
  2518. // N801A-S4_3 真空标机1 数据
  2519. #region N801A-S4_3 真空标机1
  2520. try
  2521. {
  2522. int d3PLC_FLAG = (int)s4PLCData["d3PLC_FLAG"];
  2523. int d3MES_FLAG = (int)s4PLCData["d3MES_FLAG"];
  2524. int d3PLC_FLAGOld = (int)s4PLCSignal_Old["d3PLC_FLAG"];
  2525. if (d3PLC_FLAG != d3PLC_FLAGOld)
  2526. {
  2527. if (d3PLC_FLAG == 1 && d3MES_FLAG == 0) // 0->1
  2528. {
  2529. int stationType = (int)s4PLCData["d3Type"];
  2530. if (stationType == 1)
  2531. {
  2532. // S4_3进站接口
  2533. Task.Run(() => S4_3进站接口(plcNo, stationNameStr)); // MreTasks[3].Set();
  2534. }
  2535. else if (stationType == 2)
  2536. {
  2537. // S4_3出站接口
  2538. Task.Run(() => S4_3出站接口(plcNo, stationNameStr)); // MreTasks[3].Set();
  2539. }
  2540. }
  2541. //else if (d3PLC_FLAG == 0 && d3MES_FLAG != 0)
  2542. //Funs[plcNo].WriteMultipleRegisters<short>(2463, (short)0);
  2543. s4PLCSignal_Old["d3PLC_FLAG"] = s4PLCData["d3PLC_FLAG"];
  2544. }
  2545. }
  2546. catch (Exception ex)
  2547. {
  2548. //Funs[plcNo].WriteMultipleRegisters<short>(2463, (short)4); // 4代表上位机报警
  2549. string str = ex.StackTrace;
  2550. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 上传标机出站接口出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  2551. }
  2552. #endregion N801A-S4_3 真空标机1
  2553. // N801A-S4_4 真空标机2 数据
  2554. #region N801A-S4_4 真空标机2
  2555. try
  2556. {
  2557. int d4PLC_FLAG = (int)s4PLCData["d4PLC_FLAG"];
  2558. int d4MES_FLAG = (int)s4PLCData["d4MES_FLAG"];
  2559. int d4PLC_FLAGOld = (int)s4PLCSignal_Old["d4PLC_FLAG"];
  2560. if (d4PLC_FLAG != d4PLC_FLAGOld)
  2561. {
  2562. if (d4PLC_FLAG == 1 && d4MES_FLAG == 0) // 0->1
  2563. {
  2564. int stationType = (int)s4PLCData["d4Type"];
  2565. if (stationType == 1)
  2566. {
  2567. // S4_4进站接口
  2568. Task.Run(() => S4_4进站接口(plcNo, stationNameStr)); // MreTasks[3].Set();
  2569. }
  2570. else if (stationType == 2)
  2571. {
  2572. // S4_4出站接口
  2573. Task.Run(() => S4_4出站接口(plcNo, stationNameStr)); // MreTasks[3].Set();
  2574. }
  2575. }
  2576. //else if (d4PLC_FLAG == 0 && d4MES_FLAG != 0)
  2577. //Funs[plcNo].WriteMultipleRegisters<short>(2496, (short)0);
  2578. s4PLCSignal_Old["d4PLC_FLAG"] = s4PLCData["d4PLC_FLAG"];
  2579. }
  2580. }
  2581. catch (Exception ex)
  2582. {
  2583. //Funs[plcNo].WriteMultipleRegisters<short>(2496, (short)4); // 4代表上位机报警
  2584. string str = ex.StackTrace;
  2585. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 上传标机出站接口出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  2586. }
  2587. #endregion N801A-S4_4 真空标机2
  2588. // N801A-S4_5 弹夹扫码 数据
  2589. #region N801A-S4_5 弹夹扫码
  2590. try
  2591. {
  2592. int d5BulletclipScanCode = (int)s4PLCData["d5BulletclipScanCode"];
  2593. int d5BulletclipScanCodeOld = (int)s4PLCSignal_Old["d5BulletclipScanCode"];
  2594. if (d5BulletclipScanCode != d5BulletclipScanCodeOld)
  2595. {
  2596. if (d5BulletclipScanCode == 1) // 0->1
  2597. Task.Run(() => S4_5弹夹扫码(plcNo, stationNameStr5)); // MreTasks[1].Set();
  2598. s4PLCSignal_Old["d5BulletclipScanCode"] = s4PLCData["d5BulletclipScanCode"];
  2599. }
  2600. }
  2601. catch (Exception ex)
  2602. {
  2603. //Funs[plcNo].WriteMultipleRegisters<short>(2528, (short)6); // 6代表上位机报警
  2604. string str = ex.StackTrace;
  2605. AddMessage_Station(stationNameStr5, LogType.Error, $"PLC{plcNo}_{stationNameStr5} 弹夹扫码出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  2606. }
  2607. #endregion N801A-S4_5 弹夹扫码
  2608. // N801A-S4_5 载具扫码 数据
  2609. #region N801A-S4_5 载具扫码
  2610. try
  2611. {
  2612. int d5VehicleScanCode = (int)s4PLCData["d5VehicleScanCode"];
  2613. int d5VehicleScanCodeOld = (int)s4PLCSignal_Old["d5VehicleScanCode"];
  2614. if (d5VehicleScanCode != d5VehicleScanCodeOld)
  2615. {
  2616. if (d5VehicleScanCode == 1) // 0->1
  2617. Task.Run(() => S4_5载具扫码(plcNo, stationNameStr5)); // MreTasks[1].Set();
  2618. s4PLCSignal_Old["d5VehicleScanCode"] = s4PLCData["d5VehicleScanCode"];
  2619. }
  2620. }
  2621. catch (Exception ex)
  2622. {
  2623. //Funs[plcNo].WriteMultipleRegisters<short>(2559, (short)6); // 6代表上位机报警
  2624. string str = ex.StackTrace;
  2625. AddMessage_Station(stationNameStr5, LogType.Error, $"PLC{plcNo}_{stationNameStr5} 载具扫码出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  2626. }
  2627. #endregion N801A-S4_5 载具扫码
  2628. // N801A-S4_5 出站接口(扫完所有码后立即上传) 数据
  2629. #region N801A-S4_5 出站接口
  2630. try
  2631. {
  2632. int d5PLC_FLAG = (int)s4PLCData["d5PLC_FLAG"];
  2633. int d5MES_FLAG = (int)s4PLCData["d5MES_FLAG"];
  2634. int d5PLC_FLAGOld = (int)s4PLCSignal_Old["d5PLC_FLAG"];
  2635. if (d5PLC_FLAG != d5PLC_FLAGOld)
  2636. {
  2637. if (d5PLC_FLAG == 1 && d5MES_FLAG == 0) // 0->1
  2638. Task.Run(() => S4_5出站接口(plcNo, stationCode5, stationName5)); // MreTasks[3].Set();
  2639. //else if (d5PLC_FLAG == 0 && d5MES_FLAG != 0)
  2640. //Funs[plcNo].WriteMultipleRegisters<short>(2591, (short)0);
  2641. s4PLCSignal_Old["d5PLC_FLAG"] = s4PLCData["d5PLC_FLAG"];
  2642. }
  2643. }
  2644. catch (Exception ex)
  2645. {
  2646. //Funs[plcNo].WriteMultipleRegisters<short>(2591, (short)6); // 6代表上位机报警
  2647. string str = ex.StackTrace;
  2648. AddMessage_Station(stationNameStr5, LogType.Error, $"PLC{plcNo}_{stationNameStr5} 上传出站接口出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  2649. }
  2650. #endregion N801A-S4_5 出站接口
  2651. // N801A-S4_5 节拍接口 数据
  2652. #region N801A-S4_5 节拍接口
  2653. try
  2654. {
  2655. int d5OEEPLC_FLAG = (int)s4PLCData["d5OEEPLC_FLAG"];
  2656. int d5OEEMES_FLAG = (int)s4PLCData["d5OEEMES_FLAG"];
  2657. int d5OEEPLC_FLAGOld = (int)s4PLCSignal_Old["d5OEEPLC_FLAG"];
  2658. if (d5OEEPLC_FLAG != d5OEEPLC_FLAGOld)
  2659. {
  2660. if (d5OEEPLC_FLAG == 1 && d5OEEMES_FLAG == 0) // 0->1
  2661. Task.Run(() => S4_5节拍接口(plcNo, stationNameStr5)); // MreTasks[4].Set();
  2662. //else if (d5OEEPLC_FLAG == 0 && d5OEEMES_FLAG != 0)
  2663. //Funs[plcNo].WriteMultipleRegisters<short>(2924, (short)0);
  2664. s4PLCSignal_Old["d5OEEPLC_FLAG"] = s4PLCData["d5OEEPLC_FLAG"];
  2665. }
  2666. }
  2667. catch (Exception ex)
  2668. {
  2669. //Funs[plcNo].WriteMultipleRegisters<short>(2924, (short)4); // 4代表上位机报警
  2670. string str = ex.StackTrace;
  2671. AddMessage_Station(stationNameStr5, LogType.Error, $"PLC{plcNo}_{stationNameStr5} 上传节拍接口出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  2672. }
  2673. #endregion N801A-S4_5 节拍接口
  2674. UpdatePLCMonitor(1, plcNo, 1); // 更新PLC状态的UI // 更新PLC状态的UI
  2675. stopwatch1.Stop();
  2676. //if (stopwatch1.ElapsedMilliseconds > 60) // ZS 稳定后取消注释该项
  2677. OnMessage(LogType.Info, $"循环读取PLC数据一次,总用时{stopwatch1.ElapsedMilliseconds}ms[读取用时{stopwatch2.ElapsedMilliseconds}ms]");
  2678. }
  2679. else
  2680. {
  2681. UpdatePLCMonitor(1, plcNo, 0); // 更新PLC状态的UI
  2682. AddMessage_Station(stationNameStr, LogType.Info, "PLC" + plcNo.ToString() + "_" + stationNameStr + "连接失败!");
  2683. Funs[plcNo].Connect();
  2684. }
  2685. }
  2686. catch (Exception ex)
  2687. {
  2688. UpdatePLCMonitor(1, plcNo, 0); // 更新PLC状态的UI
  2689. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr}运行出错!错误信息:" + ex.Message.ToString());
  2690. //Funs[plcNo].ReConnect();
  2691. }
  2692. Thread.Sleep(IntervalReadPLC);
  2693. }
  2694. }
  2695. /// <summary>
  2696. /// [S4] 取放桁架 - S4_1弹夹扫码
  2697. /// </summary>
  2698. /// <param name="plcNo">PLC编号</param>
  2699. /// <param name="stationNameStr">工站全称</param>
  2700. private void S4_1弹夹扫码(int plcNo, string stationNameStr)
  2701. {
  2702. Stopwatch stopwatch1 = new Stopwatch();
  2703. Stopwatch stopwatch2 = new Stopwatch();
  2704. try
  2705. {
  2706. stopwatch1.Start();
  2707. // ZS 弹夹扫码
  2708. string d1BulletclipCode = " "; // 扫到的码
  2709. short d1BulletclipScanCode = 2;
  2710. stopwatch2.Start();
  2711. //Funs[plcNo].WriteMultipleRegisters<string>(2003, d1BulletclipCode, 20);
  2712. //// MES_Flag
  2713. //Funs[plcNo].WriteMultipleRegisters<short>(2002, d1BulletclipScanCode); // plc发送1代表请求扫码,上位机发送2代表扫码OK,3代表扫码NG,6代表上位机报警;7s未给结果代表扫码超时(扫不到码);请求前200ms确保 扫码信号 为0;
  2714. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  2715. writeToPLC_Flag.Name = "d1BulletclipScanCode";
  2716. writeToPLC_Flag.Adress = 2002;
  2717. writeToPLC_Flag.Value = d1BulletclipScanCode;
  2718. writeToPLC_Flag.WriteToPLCDatas.Add(new WriteToPLC_Data() // 穴位1物料SN(上位机写入)
  2719. {
  2720. Name = "d1BulletclipCode",
  2721. Adress = 2003,
  2722. ValueType = PLCValueType.String,
  2723. ValueTypeStrLength = 20,
  2724. Value = d1BulletclipCode
  2725. });
  2726. SxPLCWriteData_Add(ref s4PLCWriteData, "d1BulletclipScanCode", writeToPLC_Flag);
  2727. stopwatch2.Stop();
  2728. }
  2729. catch (Exception ex)
  2730. {
  2731. string str = ex.StackTrace;
  2732. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 弹夹扫码出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  2733. stopwatch2.Start();
  2734. //Funs[plcNo].WriteMultipleRegisters<string>(2003, " ", 20);
  2735. //// MES_Flag
  2736. //Funs[plcNo].WriteMultipleRegisters<short>(2002, (short)6); // 6代表上位机报警
  2737. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  2738. writeToPLC_Flag.Name = "d1BulletclipScanCode";
  2739. writeToPLC_Flag.Adress = 2002;
  2740. writeToPLC_Flag.Value = (short)6;
  2741. writeToPLC_Flag.WriteToPLCDatas.Add(new WriteToPLC_Data() // 穴位1物料SN(上位机写入)
  2742. {
  2743. Name = "d1BulletclipCode",
  2744. Adress = 2003,
  2745. ValueType = PLCValueType.String,
  2746. ValueTypeStrLength = 20,
  2747. Value = " "
  2748. });
  2749. SxPLCWriteData_Add(ref s4PLCWriteData, "d1BulletclipScanCode", writeToPLC_Flag);
  2750. stopwatch2.Stop();
  2751. }
  2752. stopwatch1.Stop();
  2753. AddMessage(LogType.Info, stationNameStr + "_弹夹扫码;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  2754. }
  2755. /// <summary>
  2756. /// [S4] 取放桁架 - S4_1载具扫码
  2757. /// </summary>
  2758. /// <param name="plcNo">PLC编号</param>
  2759. /// <param name="stationNameStr">工站全称</param>
  2760. private void S4_1载具扫码(int plcNo, string stationNameStr)
  2761. {
  2762. Stopwatch stopwatch1 = new Stopwatch();
  2763. Stopwatch stopwatch2 = new Stopwatch();
  2764. try
  2765. {
  2766. stopwatch1.Start();
  2767. // ZS 载具扫码
  2768. string d1VehicleCode = " "; // 扫到的码
  2769. // 查产品SN
  2770. string partNo = " ";
  2771. short d1VehicleScanCode = 2;
  2772. #region 进站
  2773. if (!string.IsNullOrEmpty(d1VehicleCode))
  2774. {
  2775. List<TestItem> item = new List<TestItem>();
  2776. item.Add(new TestItem()
  2777. {
  2778. Parameter_name = "载具码",
  2779. Parameter_value = d1VehicleCode,
  2780. });
  2781. item.Add(new TestItem()
  2782. {
  2783. Parameter_name = "载具穴号",
  2784. Parameter_value = "1",
  2785. });
  2786. stopwatch2.Start();
  2787. int result = SaveStationInData(stationNameStr, GlobalContext.WorkOrderCode, GlobalContext.Mtltmrk, partNo, item);
  2788. stopwatch2.Stop();
  2789. d1VehicleScanCode = (short)result == 1 ? d1VehicleScanCode : (short)result;
  2790. }
  2791. #endregion 进站
  2792. //Funs[plcNo].WriteMultipleRegisters<string>(2034, d1VehicleCode, 20);
  2793. //// MES_Flag
  2794. //Funs[plcNo].WriteMultipleRegisters<short>(2033, d1VehicleScanCode); // plc发送1代表请求扫码,上位机发送2代表扫码OK,3代表扫码NG,6代表上位机报警;7s未给结果代表扫码超时(扫不到码);请求前200ms确保 扫码信号 为0;
  2795. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  2796. writeToPLC_Flag.Name = "d1VehicleScanCode";
  2797. writeToPLC_Flag.Adress = 2033;
  2798. writeToPLC_Flag.Value = d1VehicleScanCode;
  2799. writeToPLC_Flag.WriteToPLCDatas.Add(new WriteToPLC_Data()
  2800. {
  2801. Name = "d1VehicleCode",
  2802. Adress = 2034,
  2803. ValueType = PLCValueType.String,
  2804. ValueTypeStrLength = 20,
  2805. Value = d1VehicleCode
  2806. });
  2807. SxPLCWriteData_Add(ref s4PLCWriteData, "d1VehicleScanCode", writeToPLC_Flag);
  2808. }
  2809. catch (Exception ex)
  2810. {
  2811. string str = ex.StackTrace;
  2812. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 载具扫码出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  2813. stopwatch2.Start();
  2814. //Funs[plcNo].WriteMultipleRegisters<string>(2034, " ", 20);
  2815. //// MES_Flag
  2816. //Funs[plcNo].WriteMultipleRegisters<short>(2033, (short)6); // 6代表上位机报警
  2817. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  2818. writeToPLC_Flag.Name = "d1VehicleScanCode";
  2819. writeToPLC_Flag.Adress = 2033;
  2820. writeToPLC_Flag.Value = (short)6; // 6代表上位机报警
  2821. writeToPLC_Flag.WriteToPLCDatas.Add(new WriteToPLC_Data()
  2822. {
  2823. Name = "d1VehicleCode",
  2824. Adress = 2034,
  2825. ValueType = PLCValueType.String,
  2826. ValueTypeStrLength = 20,
  2827. Value = " "
  2828. });
  2829. SxPLCWriteData_Add(ref s4PLCWriteData, "d1VehicleScanCode", writeToPLC_Flag);
  2830. stopwatch2.Stop();
  2831. }
  2832. stopwatch1.Stop();
  2833. AddMessage(LogType.Info, stationNameStr + "_载具扫码;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  2834. }
  2835. // 上次采集到的SN
  2836. //private string sn_S4_1出站接口 = string.Empty;
  2837. /// <summary>
  2838. /// [S4] 取放桁架 - S4_1出站接口
  2839. /// </summary>
  2840. private void S4_1出站接口(int plcNo, string stationCode, string stationName)
  2841. {
  2842. Stopwatch stopwatch1 = new Stopwatch();
  2843. Stopwatch stopwatch2 = new Stopwatch();
  2844. string equipmentCode = GlobalContext.LineCode + "-" + stationCode; // 设备编号
  2845. string stationNameStr = stationCode + stationName;
  2846. string processItem = stationName; // 测试项目
  2847. try
  2848. {
  2849. stopwatch1.Start();
  2850. string workorder_code = GlobalContext.WorkOrderCode; // 工单号
  2851. string batch_num = GlobalContext.BatchNumber; // 批次号
  2852. string mtltmrk = GlobalContext.Mtltmrk; // 产品型号
  2853. string plcDate_YMD = DateTime.Now.ToString("yyyyMMdd");
  2854. string supplierCode = ""; // 供应商代码
  2855. string sn = (string)s4PLCData["d1ProductSN"]; // 产品SN(弹夹码)
  2856. sn = sn.Replace("\0", "");
  2857. string d1VehicleCode1 = (string)s4PLCData["d1VehicleCode1"]; // 载具1码(弹夹穴位1)
  2858. string d1VehicleCode2 = (string)s4PLCData["d1VehicleCode2"]; // 载具2码(弹夹穴位2)
  2859. string d1VehicleCode3 = (string)s4PLCData["d1VehicleCode3"]; // 载具3码(弹夹穴位3)
  2860. string d1VehicleCode4 = (string)s4PLCData["d1VehicleCode4"]; // 载具4码(弹夹穴位4)
  2861. string d1VehicleCode5 = (string)s4PLCData["d1VehicleCode5"]; // 载具5码(弹夹穴位5)
  2862. string d1VehicleCode6 = (string)s4PLCData["d1VehicleCode6"]; // 载具6码(弹夹穴位6)
  2863. string d1VehicleCode7 = (string)s4PLCData["d1VehicleCode7"]; // 载具7码(弹夹穴位7)
  2864. string d1VehicleCode8 = (string)s4PLCData["d1VehicleCode8"]; // 载具8码(弹夹穴位8)
  2865. string d1VehicleCode9 = (string)s4PLCData["d1VehicleCode9"]; // 载具9码(弹夹穴位9)
  2866. string d1VehicleCode10 = (string)s4PLCData["d1VehicleCode10"]; // 载具10码(弹夹穴位10)
  2867. string d1VehicleCode11 = (string)s4PLCData["d1VehicleCode11"]; // 载具11码(弹夹穴位11)
  2868. string d1VehicleCode12 = (string)s4PLCData["d1VehicleCode12"]; // 载具12码(弹夹穴位12)
  2869. string d1VehicleCode13 = (string)s4PLCData["d1VehicleCode13"]; // 载具13码(弹夹穴位13)
  2870. string d1VehicleCode14 = (string)s4PLCData["d1VehicleCode14"]; // 载具14码(弹夹穴位14)
  2871. string d1VehicleCode15 = (string)s4PLCData["d1VehicleCode15"]; // 载具15码(弹夹穴位15)
  2872. int d1Result = (int)s4PLCData["d1Result"]; // 产品结果
  2873. bool pass = d1Result == 1;
  2874. List<TestItem> items1 = new List<TestItem>();
  2875. items1.Add(new TestItem()
  2876. {
  2877. Parameter_name = "产品结果",
  2878. Parameter_value = d1Result == 1 ? "OK" : "NG",
  2879. Parameter_unit = ""
  2880. });
  2881. int result1 = SwitctProcessData(stationNameStr, items1, equipmentCode, processItem
  2882. , workorder_code, batch_num, mtltmrk, plcDate_YMD, supplierCode, sn, pass, d1VehicleCode1, "1");
  2883. //int result = result1 == 1 ? 1 : (GlobalContext.IsSendProcessData ? 4 : 1);
  2884. short result = result1 == 1 ? (short)1 : (short)3;
  2885. stopwatch2.Start();
  2886. // MES_Flag 为4MES报错
  2887. //Funs[plcNo].WriteMultipleRegisters<short>(2065, result); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  2888. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  2889. writeToPLC_Flag.Name = "d1MES_FLAG";
  2890. writeToPLC_Flag.Adress = 2065;
  2891. writeToPLC_Flag.Value = result;
  2892. SxPLCWriteData_Add(ref s4PLCWriteData, "d1MES_FLAG", writeToPLC_Flag);
  2893. stopwatch2.Stop();
  2894. WritePLCLog(LogType.Debug, $"PLC{plcNo}_[{equipmentCode}]{processItem}-Write" + (result == 1 ? "成功!" : "失败!"));
  2895. }
  2896. catch (Exception ex)
  2897. {
  2898. stopwatch2.Start();
  2899. // MES_Flag 为4上位机报错
  2900. //Funs[plcNo].WriteMultipleRegisters<short>(2065, (short)4); // 4代表上位机报警
  2901. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  2902. writeToPLC_Flag.Name = "d1MES_FLAG";
  2903. writeToPLC_Flag.Adress = 2065;
  2904. writeToPLC_Flag.Value = (short)4;
  2905. SxPLCWriteData_Add(ref s4PLCWriteData, "d1MES_FLAG", writeToPLC_Flag);
  2906. stopwatch2.Stop();
  2907. string str = ex.StackTrace;
  2908. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_[{equipmentCode}]{processItem}上传出站接口!错误信息:" + ex.Message.ToString() + ";异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  2909. }
  2910. stopwatch1.Stop();
  2911. AddMessage(LogType.Info, stationNameStr + "_出站接口;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  2912. }
  2913. /// <summary>
  2914. /// [S4] 取放桁架 - S4_1节拍接口
  2915. /// </summary>
  2916. /// <param name="plcNo">PLC编号</param>
  2917. /// <param name="stationNameStr">工站全称</param>
  2918. private void S4_1节拍接口(int plcNo, string stationNameStr)
  2919. {
  2920. Stopwatch stopwatch1 = new Stopwatch();
  2921. Stopwatch stopwatch2 = new Stopwatch();
  2922. string resultStr = string.Empty;
  2923. try
  2924. {
  2925. stopwatch1.Start();
  2926. string oEEType = ((int)s4PLCData["d1OEEType"]).ToString(); // 节拍类型(plc写入)
  2927. string d1OEEProductSN = (string)s4PLCData["d1OEEProductSN"]; // 载具SN
  2928. d1OEEProductSN = d1OEEProductSN.Replace("\0", "");
  2929. bool actionBool = Enum.TryParse(oEEType, out XiaomiDeviceOEE deviceOEE);
  2930. if (!actionBool)
  2931. {
  2932. stopwatch2.Start();
  2933. // MES_Flag
  2934. //Funs[plcNo].WriteMultipleRegisters<short>(2398, (short)4); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  2935. WriteToPLC_Flag writeToPLC_Flag1 = new WriteToPLC_Flag(); // MES_Flag
  2936. writeToPLC_Flag1.Name = "d1OEEMES_FLAG";
  2937. writeToPLC_Flag1.Adress = 2398;
  2938. writeToPLC_Flag1.Value = (short)4;
  2939. SxPLCWriteData_Add(ref s4PLCWriteData, "d1OEEMES_FLAG", writeToPLC_Flag1);
  2940. stopwatch2.Stop();
  2941. AddMessage(LogType.Info, stationNameStr + $"_节拍接口-- 设备上传了未识别的节拍类型【{oEEType}】请检查;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  2942. return;
  2943. }
  2944. string d1OEEPartNo = string.Empty; // 物料码
  2945. if (string.IsNullOrEmpty(d1OEEProductSN))
  2946. {
  2947. stopwatch2.Start();
  2948. // MES_Flag
  2949. //Funs[plcNo].WriteMultipleRegisters<short>(2398, (short)1); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  2950. WriteToPLC_Flag writeToPLC_Flag1 = new WriteToPLC_Flag(); // MES_Flag
  2951. writeToPLC_Flag1.Name = "d1OEEMES_FLAG";
  2952. writeToPLC_Flag1.Adress = 2398;
  2953. writeToPLC_Flag1.Value = (short)1;
  2954. SxPLCWriteData_Add(ref s4PLCWriteData, "d1OEEMES_FLAG", writeToPLC_Flag1);
  2955. stopwatch2.Stop();
  2956. AddMessage(LogType.Info, stationNameStr + $"_节拍接口-- 上传内容无效已自动省略;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  2957. return;
  2958. }
  2959. else
  2960. { // 查产品SN
  2961. d1OEEPartNo = "Test"; // ZS
  2962. }
  2963. short d1OEEMES_FLAG = 0;
  2964. // 上传OEE
  2965. (short, string) result = SaveOEEData(plcNo, stationNameStr, deviceOEE, d1OEEPartNo, d1OEEProductSN);
  2966. d1OEEMES_FLAG = result.Item1;
  2967. resultStr = result.Item2;
  2968. stopwatch2.Start();
  2969. // MES_Flag
  2970. //Funs[plcNo].WriteMultipleRegisters<short>(2398, d1OEEMES_FLAG); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  2971. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  2972. writeToPLC_Flag.Name = "d1OEEMES_FLAG";
  2973. writeToPLC_Flag.Adress = 2398;
  2974. writeToPLC_Flag.Value = d1OEEMES_FLAG;
  2975. SxPLCWriteData_Add(ref s4PLCWriteData, "d1OEEMES_FLAG", writeToPLC_Flag);
  2976. stopwatch2.Stop();
  2977. }
  2978. catch (Exception ex)
  2979. {
  2980. string str = ex.StackTrace;
  2981. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 节拍接口出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  2982. // MES_Flag
  2983. stopwatch2.Start();
  2984. //Funs[plcNo].WriteMultipleRegisters<short>(2398, (short)4); // 4代表上位机报警
  2985. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  2986. writeToPLC_Flag.Name = "d1OEEMES_FLAG";
  2987. writeToPLC_Flag.Adress = 2398;
  2988. writeToPLC_Flag.Value = (short)4;
  2989. SxPLCWriteData_Add(ref s4PLCWriteData, "d1OEEMES_FLAG", writeToPLC_Flag);
  2990. stopwatch2.Stop();
  2991. }
  2992. stopwatch1.Stop();
  2993. AddMessage(LogType.Info, stationNameStr + $"_节拍接口-- {resultStr};总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  2994. }
  2995. /// <summary>
  2996. /// [S4] 取放桁架 - S4_2桁架
  2997. /// </summary>
  2998. /// <param name="plcNo">PLC编号</param>
  2999. /// <param name="stationNameStr">工站全称</param>
  3000. private void S4_2桁架(int plcNo, string stationNameStr)
  3001. {
  3002. Stopwatch stopwatch1 = new Stopwatch();
  3003. Stopwatch stopwatch2 = new Stopwatch();
  3004. try
  3005. {
  3006. stopwatch1.Start();
  3007. // ZS 弹夹扫码
  3008. string d2BulletclipCode = " "; // 扫到的码
  3009. short d2BulletclipStates = 1; // 弹夹状态(上位机写入)
  3010. short d2BulletclipScanCode = 2;
  3011. stopwatch2.Start();
  3012. //Funs[plcNo].WriteMultipleRegisters<string>(2432, d2BulletclipCode, 20); // 扫到的码
  3013. //Funs[plcNo].WriteMultipleRegisters<short>(2431, d2BulletclipStates); // 弹夹状态(上位机写入)
  3014. //// MES_Flag
  3015. //Funs[plcNo].WriteMultipleRegisters<short>(2430, d2BulletclipScanCode); // plc发送1代表请求扫码,上位机发送2代表扫码OK,3代表扫码NG,6代表上位机报警;7s未给结果代表扫码超时(扫不到码);请求前200ms确保 扫码信号 为0;
  3016. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  3017. writeToPLC_Flag.Name = "d2BulletclipScanCode";
  3018. writeToPLC_Flag.Adress = 2430;
  3019. writeToPLC_Flag.Value = d2BulletclipScanCode;
  3020. writeToPLC_Flag.WriteToPLCDatas.Add(new WriteToPLC_Data()
  3021. {
  3022. Name = "d2BulletclipCode",
  3023. Adress = 2432,
  3024. ValueType = PLCValueType.String,
  3025. ValueTypeStrLength = 20,
  3026. Value = d2BulletclipCode
  3027. });
  3028. writeToPLC_Flag.WriteToPLCDatas.Add(new WriteToPLC_Data()
  3029. {
  3030. Name = "d2BulletclipStates",
  3031. Adress = 2431,
  3032. ValueType = PLCValueType.Short,
  3033. Value = d2BulletclipStates
  3034. });
  3035. SxPLCWriteData_Add(ref s4PLCWriteData, "d2BulletclipScanCode", writeToPLC_Flag);
  3036. stopwatch2.Stop();
  3037. }
  3038. catch (Exception ex)
  3039. {
  3040. string str = ex.StackTrace;
  3041. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 弹夹扫码出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  3042. stopwatch2.Start();
  3043. //Funs[plcNo].WriteMultipleRegisters<string>(2432, " ", 20);
  3044. //Funs[plcNo].WriteMultipleRegisters<short>(2431, (short)0);
  3045. // MES_Flag
  3046. //Funs[plcNo].WriteMultipleRegisters<short>(2430, (short)6); // 6代表上位机报警
  3047. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  3048. writeToPLC_Flag.Name = "d2BulletclipScanCode";
  3049. writeToPLC_Flag.Adress = 2430;
  3050. writeToPLC_Flag.Value = (short)6;
  3051. writeToPLC_Flag.WriteToPLCDatas.Add(new WriteToPLC_Data()
  3052. {
  3053. Name = "d2BulletclipCode",
  3054. Adress = 2432,
  3055. ValueType = PLCValueType.String,
  3056. ValueTypeStrLength = 20,
  3057. Value = " "
  3058. });
  3059. writeToPLC_Flag.WriteToPLCDatas.Add(new WriteToPLC_Data()
  3060. {
  3061. Name = "d2BulletclipStates",
  3062. Adress = 2431,
  3063. ValueType = PLCValueType.Short,
  3064. Value = (short)0
  3065. });
  3066. SxPLCWriteData_Add(ref s4PLCWriteData, "d2BulletclipScanCode", writeToPLC_Flag);
  3067. stopwatch2.Stop();
  3068. }
  3069. stopwatch1.Stop();
  3070. AddMessage(LogType.Info, stationNameStr + "_弹夹扫码;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  3071. }
  3072. // 上次采集到的SN
  3073. //private string sn_S4_3进站接口 = string.Empty;
  3074. /// <summary>
  3075. /// [S4] 取放桁架 - S4_3进站接口(提升机1)
  3076. /// </summary>
  3077. private void S4_3进站接口(int plcNo, string stationNameStr)
  3078. {
  3079. Stopwatch stopwatch1 = new Stopwatch();
  3080. Stopwatch stopwatch2 = new Stopwatch();
  3081. try
  3082. {
  3083. stopwatch1.Start();
  3084. string sn = (string)s4PLCData["d3ProductSN"]; // 产品SN(弹夹码)
  3085. sn = sn.Replace("\0", "");
  3086. int d3Result = (int)s4PLCData["d3Result"]; // 产品结果
  3087. // ZS 查询15个载具码与15个产品SN
  3088. List<string> vehicleCodes = new string[15].ToList();
  3089. List<string> portNos = new string[15].ToList();
  3090. // 调用MES进站(最多15个)
  3091. stopwatch2.Start();
  3092. List<int> results = new int[15].ToList(); // 结果集;0代表产品为空
  3093. for (int i = 0; i < vehicleCodes.Count; i++)
  3094. {
  3095. // 循环进站
  3096. if (!string.IsNullOrEmpty(vehicleCodes[i]))
  3097. {
  3098. // 产品SN(物料码)校验
  3099. string portNo = portNos[i];
  3100. List<TestItem> item = new List<TestItem>();
  3101. item.Add(new TestItem()
  3102. {
  3103. Parameter_name = "弹夹码",
  3104. Parameter_value = sn,
  3105. });
  3106. item.Add(new TestItem()
  3107. {
  3108. Parameter_name = "弹夹穴位",
  3109. Parameter_value = (i + 1).ToString(),
  3110. });
  3111. item.Add(new TestItem()
  3112. {
  3113. Parameter_name = "载具码",
  3114. Parameter_value = vehicleCodes[i],
  3115. });
  3116. item.Add(new TestItem()
  3117. {
  3118. Parameter_name = "载具穴号",
  3119. Parameter_value = "1",
  3120. });
  3121. results[i] = SaveStationInData(stationNameStr, GlobalContext.WorkOrderCode, GlobalContext.Mtltmrk, portNo, item);
  3122. }
  3123. }
  3124. stopwatch2.Stop();
  3125. short result = 0;
  3126. bool haveMesWarn = results.Contains(5);
  3127. bool havePCWarn = results.Contains(6);
  3128. if (haveMesWarn)
  3129. result = 2; // 5->2
  3130. else if (havePCWarn)
  3131. result = 6; // 6->4
  3132. else
  3133. result = 1;
  3134. // MES_Flag 为4MES报错
  3135. //Funs[plcNo].WriteMultipleRegisters<short>(2463, result); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  3136. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  3137. writeToPLC_Flag.Name = "d3MES_FLAG";
  3138. writeToPLC_Flag.Adress = 2463;
  3139. writeToPLC_Flag.Value = result;
  3140. SxPLCWriteData_Add(ref s4PLCWriteData, "d3MES_FLAG", writeToPLC_Flag);
  3141. WritePLCLog(LogType.Debug, $"PLC{plcNo}_{stationNameStr}-Write" + (result == 1 ? "成功!" : "失败!"));
  3142. }
  3143. catch (Exception ex)
  3144. {
  3145. stopwatch2.Stop();
  3146. // MES_Flag 为4上位机报错
  3147. //Funs[plcNo].WriteMultipleRegisters<short>(2463, (short)4); // 4代表上位机报警
  3148. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  3149. writeToPLC_Flag.Name = "d3MES_FLAG";
  3150. writeToPLC_Flag.Adress = 2463;
  3151. writeToPLC_Flag.Value = (short)4;
  3152. SxPLCWriteData_Add(ref s4PLCWriteData, "d3MES_FLAG", writeToPLC_Flag);
  3153. string str = ex.StackTrace;
  3154. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr}S4_3进站接口!错误信息:" + ex.Message.ToString() + ";异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  3155. }
  3156. stopwatch1.Stop();
  3157. AddMessage(LogType.Info, stationNameStr + "_S4_3进站接口;总用时" + stopwatch1.ElapsedMilliseconds + "ms;调用MES用时" + stopwatch2.ElapsedMilliseconds + "ms");
  3158. }
  3159. // 上次采集到的SN
  3160. //private string sn_S4_3出站接口 = string.Empty;
  3161. /// <summary>
  3162. /// [S4] 取放桁架 - S4_3出站接口(提升机1)
  3163. /// </summary>
  3164. private void S4_3出站接口(int plcNo, string stationNameStr)
  3165. {
  3166. Stopwatch stopwatch1 = new Stopwatch();
  3167. Stopwatch stopwatch2 = new Stopwatch();
  3168. try
  3169. {
  3170. stopwatch1.Start();
  3171. string workorder_code = GlobalContext.WorkOrderCode; // 工单号
  3172. string batch_num = GlobalContext.BatchNumber; // 批次号
  3173. string mtltmrk = GlobalContext.Mtltmrk; // 产品型号
  3174. string plcDate_YMD = DateTime.Now.ToString("yyyyMMdd");
  3175. string supplierCode = ""; // 供应商代码
  3176. string sn = (string)s4PLCData["d3ProductSN"]; // 产品SN(弹夹码)
  3177. sn = sn.Replace("\0", "");
  3178. int d3Result = (int)s4PLCData["d3Result"]; // 产品结果
  3179. bool isPass = d3Result == 1; // 产品结果 bool
  3180. // ZS 查询15个载具码与15个产品SN
  3181. List<string> vehicleCodes = new string[15].ToList();
  3182. List<string> portNos = new string[15].ToList();
  3183. // 调用MES出站
  3184. stopwatch2.Start();
  3185. List<int> results = new int[15].ToList(); // 结果集;0代表产品为空
  3186. for (int i = 0; i < vehicleCodes.Count; i++)
  3187. {
  3188. // 循环出站
  3189. if (!string.IsNullOrEmpty(vehicleCodes[i]))
  3190. {
  3191. string portNo = portNos[i];
  3192. List<TestItem> items1 = new List<TestItem>();
  3193. items1.Add(new TestItem()
  3194. {
  3195. Parameter_name = "弹夹码",
  3196. Parameter_value = sn,
  3197. });
  3198. items1.Add(new TestItem()
  3199. {
  3200. Parameter_name = "弹夹穴位",
  3201. Parameter_value = (i + 1).ToString(),
  3202. });
  3203. items1.Add(new TestItem()
  3204. {
  3205. Parameter_name = "载具码",
  3206. Parameter_value = vehicleCodes[i],
  3207. });
  3208. items1.Add(new TestItem()
  3209. {
  3210. Parameter_name = "载具穴号",
  3211. Parameter_value = "1",
  3212. });
  3213. items1.Add(new TestItem()
  3214. {
  3215. Parameter_name = "产品结果",
  3216. Parameter_value = isPass ? "OK" : "NG",
  3217. });
  3218. int mesResult = SwitctProcessData(stationNameStr, items1, "", ""
  3219. , workorder_code, batch_num, mtltmrk, plcDate_YMD, supplierCode, portNo, isPass, vehicleCodes[i], "1");
  3220. results[i] = mesResult == 1 ? 1 : 2;
  3221. }
  3222. }
  3223. stopwatch2.Stop();
  3224. short result = 0;
  3225. bool haveMesWarn = results.Contains(2);
  3226. bool havePCWarn = results.Contains(3);
  3227. if (haveMesWarn)
  3228. result = 2; // 2->2
  3229. else if (havePCWarn)
  3230. result = 4; // 3->4
  3231. else
  3232. result = 1;
  3233. // MES_Flag 为4MES报错
  3234. //Funs[plcNo].WriteMultipleRegisters<short>(2463, result); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  3235. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  3236. writeToPLC_Flag.Name = "d3MES_FLAG";
  3237. writeToPLC_Flag.Adress = 2463;
  3238. writeToPLC_Flag.Value = result;
  3239. SxPLCWriteData_Add(ref s4PLCWriteData, "d3MES_FLAG", writeToPLC_Flag);
  3240. WritePLCLog(LogType.Debug, $"PLC{plcNo}_{stationNameStr}-Write" + (result == 1 ? "成功!" : "失败!"));
  3241. }
  3242. catch (Exception ex)
  3243. {
  3244. stopwatch2.Stop();
  3245. // MES_Flag 为4上位机报错
  3246. //Funs[plcNo].WriteMultipleRegisters<short>(2463, (short)4); // 4代表上位机报警
  3247. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  3248. writeToPLC_Flag.Name = "d3MES_FLAG";
  3249. writeToPLC_Flag.Adress = 2463;
  3250. writeToPLC_Flag.Value = (short)4;
  3251. SxPLCWriteData_Add(ref s4PLCWriteData, "d3MES_FLAG", writeToPLC_Flag);
  3252. string str = ex.StackTrace;
  3253. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr}S4_3出站接口!错误信息:" + ex.Message.ToString() + ";异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  3254. }
  3255. stopwatch1.Stop();
  3256. AddMessage(LogType.Info, stationNameStr + "_S4_3出站接口;总用时" + stopwatch1.ElapsedMilliseconds + "ms;调用MES用时" + stopwatch2.ElapsedMilliseconds + "ms");
  3257. }
  3258. // 上次采集到的SN
  3259. //private string sn_S4_4进站接口 = string.Empty;
  3260. /// <summary>
  3261. /// [S4] 取放桁架 - S4_4进站接口(提升机2)
  3262. /// </summary>
  3263. private void S4_4进站接口(int plcNo, string stationNameStr)
  3264. {
  3265. Stopwatch stopwatch1 = new Stopwatch();
  3266. Stopwatch stopwatch2 = new Stopwatch();
  3267. try
  3268. {
  3269. stopwatch1.Start();
  3270. string sn = (string)s4PLCData["d4ProductSN"]; // 产品SN(弹夹码)
  3271. sn = sn.Replace("\0", "");
  3272. int d4Result = (int)s4PLCData["d4Result"]; // 产品结果
  3273. // ZS 查询15个载具码与15个产品SN
  3274. List<string> vehicleCodes = new string[15].ToList();
  3275. List<string> portNos = new string[15].ToList();
  3276. // 调用MES进站(最多15个)
  3277. stopwatch2.Start();
  3278. List<int> results = new int[15].ToList(); // 结果集;0代表产品为空
  3279. for (int i = 0; i < vehicleCodes.Count; i++)
  3280. {
  3281. // 循环进站
  3282. if (!string.IsNullOrEmpty(vehicleCodes[i]))
  3283. {
  3284. // 产品SN(物料码)校验
  3285. string portNo = portNos[i];
  3286. List<TestItem> item = new List<TestItem>();
  3287. item.Add(new TestItem()
  3288. {
  3289. Parameter_name = "弹夹码",
  3290. Parameter_value = sn,
  3291. });
  3292. item.Add(new TestItem()
  3293. {
  3294. Parameter_name = "弹夹穴位",
  3295. Parameter_value = (i + 1).ToString(),
  3296. });
  3297. item.Add(new TestItem()
  3298. {
  3299. Parameter_name = "载具码",
  3300. Parameter_value = vehicleCodes[i],
  3301. });
  3302. item.Add(new TestItem()
  3303. {
  3304. Parameter_name = "载具穴号",
  3305. Parameter_value = "1",
  3306. });
  3307. results[i] = SaveStationInData(stationNameStr, GlobalContext.WorkOrderCode, GlobalContext.Mtltmrk, portNo, item);
  3308. }
  3309. }
  3310. stopwatch2.Stop();
  3311. short result = 0;
  3312. bool haveMesWarn = results.Contains(5);
  3313. bool havePCWarn = results.Contains(6);
  3314. if (haveMesWarn)
  3315. result = 2; // 5->2
  3316. else if (havePCWarn)
  3317. result = 6; // 6->4
  3318. else
  3319. result = 1;
  3320. // MES_Flag 为4MES报错
  3321. //Funs[plcNo].WriteMultipleRegisters<short>(2496, result); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  3322. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  3323. writeToPLC_Flag.Name = "d4MES_FLAG";
  3324. writeToPLC_Flag.Adress = 2496;
  3325. writeToPLC_Flag.Value = result;
  3326. SxPLCWriteData_Add(ref s4PLCWriteData, "d4MES_FLAG", writeToPLC_Flag);
  3327. WritePLCLog(LogType.Debug, $"PLC{plcNo}_{stationNameStr}-Write" + (result == 1 ? "成功!" : "失败!"));
  3328. }
  3329. catch (Exception ex)
  3330. {
  3331. stopwatch2.Stop();
  3332. // MES_Flag 为4上位机报错
  3333. //Funs[plcNo].WriteMultipleRegisters<short>(2496, (short)4); // 4代表上位机报警
  3334. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  3335. writeToPLC_Flag.Name = "d4MES_FLAG";
  3336. writeToPLC_Flag.Adress = 2496;
  3337. writeToPLC_Flag.Value = (short)4;
  3338. SxPLCWriteData_Add(ref s4PLCWriteData, "d4MES_FLAG", writeToPLC_Flag);
  3339. string str = ex.StackTrace;
  3340. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr}S4_4进站接口!错误信息:" + ex.Message.ToString() + ";异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  3341. }
  3342. stopwatch1.Stop();
  3343. AddMessage(LogType.Info, stationNameStr + "_S4_4进站接口;总用时" + stopwatch1.ElapsedMilliseconds + "ms;调用MES用时" + stopwatch2.ElapsedMilliseconds + "ms");
  3344. }
  3345. // 上次采集到的SN
  3346. //private string sn_S4_4出站接口 = string.Empty;
  3347. /// <summary>
  3348. /// [S4] 取放桁架 - S4_4出站接口(提升机2)
  3349. /// </summary>
  3350. private void S4_4出站接口(int plcNo, string stationNameStr)
  3351. {
  3352. Stopwatch stopwatch1 = new Stopwatch();
  3353. Stopwatch stopwatch2 = new Stopwatch();
  3354. try
  3355. {
  3356. stopwatch1.Start();
  3357. string workorder_code = GlobalContext.WorkOrderCode; // 工单号
  3358. string batch_num = GlobalContext.BatchNumber; // 批次号
  3359. string mtltmrk = GlobalContext.Mtltmrk; // 产品型号
  3360. string plcDate_YMD = DateTime.Now.ToString("yyyyMMdd");
  3361. string supplierCode = ""; // 供应商代码
  3362. string sn = (string)s4PLCData["d4ProductSN"]; // 产品SN(弹夹码)
  3363. sn = sn.Replace("\0", "");
  3364. int d4Result = (int)s4PLCData["d4Result"]; // 产品结果
  3365. bool isPass = d4Result == 1; // 产品结果 bool
  3366. // ZS 查询15个载具码与15个产品SN
  3367. List<string> vehicleCodes = new string[15].ToList();
  3368. List<string> portNos = new string[15].ToList();
  3369. // 调用MES出站
  3370. stopwatch2.Start();
  3371. List<int> results = new int[15].ToList(); // 结果集;0代表产品为空
  3372. for (int i = 0; i < vehicleCodes.Count; i++)
  3373. {
  3374. // 循环出站
  3375. if (!string.IsNullOrEmpty(vehicleCodes[i]))
  3376. {
  3377. string portNo = portNos[i];
  3378. List<TestItem> items1 = new List<TestItem>();
  3379. items1.Add(new TestItem()
  3380. {
  3381. Parameter_name = "弹夹码",
  3382. Parameter_value = sn,
  3383. });
  3384. items1.Add(new TestItem()
  3385. {
  3386. Parameter_name = "弹夹穴位",
  3387. Parameter_value = (i + 1).ToString(),
  3388. });
  3389. items1.Add(new TestItem()
  3390. {
  3391. Parameter_name = "载具码",
  3392. Parameter_value = vehicleCodes[i],
  3393. });
  3394. items1.Add(new TestItem()
  3395. {
  3396. Parameter_name = "载具穴号",
  3397. Parameter_value = "1",
  3398. });
  3399. items1.Add(new TestItem()
  3400. {
  3401. Parameter_name = "产品结果",
  3402. Parameter_value = isPass ? "OK" : "NG",
  3403. });
  3404. int mesResult = SwitctProcessData(stationNameStr, items1, "", ""
  3405. , workorder_code, batch_num, mtltmrk, plcDate_YMD, supplierCode, portNo, isPass, vehicleCodes[i], "1");
  3406. results[i] = mesResult == 1 ? 1 : 2;
  3407. }
  3408. }
  3409. stopwatch2.Stop();
  3410. short result = 0;
  3411. bool haveMesWarn = results.Contains(2);
  3412. bool havePCWarn = results.Contains(3);
  3413. if (haveMesWarn)
  3414. result = 2; // 2->2
  3415. else if (havePCWarn)
  3416. result = 4; // 3->4
  3417. else
  3418. result = 1;
  3419. // MES_Flag 为4MES报错
  3420. //Funs[plcNo].WriteMultipleRegisters<short>(2496, result); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  3421. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  3422. writeToPLC_Flag.Name = "d4MES_FLAG";
  3423. writeToPLC_Flag.Adress = 2496;
  3424. writeToPLC_Flag.Value = result;
  3425. SxPLCWriteData_Add(ref s4PLCWriteData, "d4MES_FLAG", writeToPLC_Flag);
  3426. WritePLCLog(LogType.Debug, $"PLC{plcNo}_{stationNameStr}-Write" + (result == 1 ? "成功!" : "失败!"));
  3427. }
  3428. catch (Exception ex)
  3429. {
  3430. stopwatch2.Stop();
  3431. // MES_Flag 为4上位机报错
  3432. //Funs[plcNo].WriteMultipleRegisters<short>(2496, (short)4); // 4代表上位机报警
  3433. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  3434. writeToPLC_Flag.Name = "d4MES_FLAG";
  3435. writeToPLC_Flag.Adress = 2496;
  3436. writeToPLC_Flag.Value = (short)4;
  3437. SxPLCWriteData_Add(ref s4PLCWriteData, "d4MES_FLAG", writeToPLC_Flag);
  3438. string str = ex.StackTrace;
  3439. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr}S4_4出站接口!错误信息:" + ex.Message.ToString() + ";异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  3440. }
  3441. stopwatch1.Stop();
  3442. AddMessage(LogType.Info, stationNameStr + "_S4_4出站接口;总用时" + stopwatch1.ElapsedMilliseconds + "ms;调用MES用时" + stopwatch2.ElapsedMilliseconds + "ms");
  3443. }
  3444. /// <summary>
  3445. /// [S4] 取放桁架 - S4_5弹夹扫码
  3446. /// </summary>
  3447. /// <param name="plcNo">PLC编号</param>
  3448. /// <param name="stationNameStr">工站全称</param>
  3449. private void S4_5弹夹扫码(int plcNo, string stationNameStr)
  3450. {
  3451. Stopwatch stopwatch1 = new Stopwatch();
  3452. Stopwatch stopwatch2 = new Stopwatch();
  3453. try
  3454. {
  3455. stopwatch1.Start();
  3456. // ZS 弹夹扫码
  3457. string d5BulletclipCode = " "; // 扫到的码
  3458. short d5BulletclipScanCode = 2;
  3459. stopwatch2.Start();
  3460. //Funs[plcNo].WriteMultipleRegisters<string>(2529, d5BulletclipCode, 20);
  3461. //// MES_Flag
  3462. //Funs[plcNo].WriteMultipleRegisters<short>(2528, d5BulletclipScanCode); // plc发送1代表请求扫码,上位机发送2代表扫码OK,3代表扫码NG,6代表上位机报警;7s未给结果代表扫码超时(扫不到码);请求前200ms确保 扫码信号 为0;
  3463. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  3464. writeToPLC_Flag.Name = "d5BulletclipScanCode";
  3465. writeToPLC_Flag.Adress = 2528;
  3466. writeToPLC_Flag.Value = d5BulletclipScanCode;
  3467. writeToPLC_Flag.WriteToPLCDatas.Add(new WriteToPLC_Data() // 1空;2ng;3假产品;
  3468. {
  3469. Name = "d5BulletclipCode",
  3470. Adress = 2529,
  3471. ValueType = PLCValueType.String,
  3472. ValueTypeStrLength = 20,
  3473. Value = d5BulletclipCode
  3474. });
  3475. SxPLCWriteData_Add(ref s4PLCWriteData, "d5BulletclipScanCode", writeToPLC_Flag);
  3476. stopwatch2.Stop();
  3477. }
  3478. catch (Exception ex)
  3479. {
  3480. string str = ex.StackTrace;
  3481. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 弹夹扫码出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  3482. stopwatch2.Start();
  3483. //Funs[plcNo].WriteMultipleRegisters<string>(2529, " ", 20);
  3484. //// MES_Flag
  3485. //Funs[plcNo].WriteMultipleRegisters<short>(2528, (short)6); // 6代表上位机报警
  3486. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  3487. writeToPLC_Flag.Name = "d5BulletclipScanCode";
  3488. writeToPLC_Flag.Adress = 2528;
  3489. writeToPLC_Flag.Value = (short)6;
  3490. writeToPLC_Flag.WriteToPLCDatas.Add(new WriteToPLC_Data() // 1空;2ng;3假产品;
  3491. {
  3492. Name = "d5BulletclipCode",
  3493. Adress = 2529,
  3494. ValueType = PLCValueType.String,
  3495. ValueTypeStrLength = 20,
  3496. Value = " "
  3497. });
  3498. SxPLCWriteData_Add(ref s4PLCWriteData, "d5BulletclipScanCode", writeToPLC_Flag);
  3499. stopwatch2.Stop();
  3500. }
  3501. stopwatch1.Stop();
  3502. AddMessage(LogType.Info, stationNameStr + "_弹夹扫码;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  3503. }
  3504. /// <summary>
  3505. /// [S4] 取放桁架 - S4_5载具扫码
  3506. /// </summary>
  3507. /// <param name="plcNo">PLC编号</param>
  3508. /// <param name="stationNameStr">工站全称</param>
  3509. private void S4_5载具扫码(int plcNo, string stationNameStr)
  3510. {
  3511. Stopwatch stopwatch1 = new Stopwatch();
  3512. Stopwatch stopwatch2 = new Stopwatch();
  3513. try
  3514. {
  3515. stopwatch1.Start();
  3516. // ZS 载具扫码
  3517. string d5VehicleCode = " "; // 扫到的码
  3518. // 查产品SN
  3519. string partNo = " ";
  3520. short d5VehicleScanCode = 2;
  3521. #region 进站
  3522. if (!string.IsNullOrEmpty(d5VehicleCode))
  3523. {
  3524. List<TestItem> item = new List<TestItem>();
  3525. item.Add(new TestItem()
  3526. {
  3527. Parameter_name = "载具码",
  3528. Parameter_value = d5VehicleCode,
  3529. });
  3530. item.Add(new TestItem()
  3531. {
  3532. Parameter_name = "载具穴号",
  3533. Parameter_value = "1",
  3534. });
  3535. stopwatch2.Start();
  3536. int result = SaveStationInData(stationNameStr, GlobalContext.WorkOrderCode, GlobalContext.Mtltmrk, partNo, item);
  3537. stopwatch2.Stop();
  3538. d5VehicleScanCode = (short)result == 1 ? d5VehicleScanCode : (short)result;
  3539. }
  3540. #endregion 进站
  3541. //Funs[plcNo].WriteMultipleRegisters<string>(2560, d5VehicleCode, 20);
  3542. //// MES_Flag
  3543. //Funs[plcNo].WriteMultipleRegisters<short>(2559, d5VehicleScanCode); // plc发送1代表请求扫码,上位机发送2代表扫码OK,3代表扫码NG,6代表上位机报警;7s未给结果代表扫码超时(扫不到码);请求前200ms确保 扫码信号 为0;
  3544. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  3545. writeToPLC_Flag.Name = "d5VehicleScanCode";
  3546. writeToPLC_Flag.Adress = 2559;
  3547. writeToPLC_Flag.Value = d5VehicleScanCode;
  3548. writeToPLC_Flag.WriteToPLCDatas.Add(new WriteToPLC_Data() // 1空;2ng;3假产品;
  3549. {
  3550. Name = "d5VehicleCode",
  3551. Adress = 2560,
  3552. ValueType = PLCValueType.String,
  3553. ValueTypeStrLength = 20,
  3554. Value = d5VehicleCode
  3555. });
  3556. SxPLCWriteData_Add(ref s4PLCWriteData, "d5VehicleScanCode", writeToPLC_Flag);
  3557. }
  3558. catch (Exception ex)
  3559. {
  3560. string str = ex.StackTrace;
  3561. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 载具扫码出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  3562. stopwatch2.Start();
  3563. //Funs[plcNo].WriteMultipleRegisters<string>(2560, " ", 20);
  3564. //// MES_Flag
  3565. //Funs[plcNo].WriteMultipleRegisters<short>(2559, (short)6); // 6代表上位机报警
  3566. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  3567. writeToPLC_Flag.Name = "d5VehicleScanCode";
  3568. writeToPLC_Flag.Adress = 2559;
  3569. writeToPLC_Flag.Value = (short)6;
  3570. writeToPLC_Flag.WriteToPLCDatas.Add(new WriteToPLC_Data() // 1空;2ng;3假产品;
  3571. {
  3572. Name = "d5VehicleCode",
  3573. Adress = 2560,
  3574. ValueType = PLCValueType.String,
  3575. ValueTypeStrLength = 20,
  3576. Value = " "
  3577. });
  3578. SxPLCWriteData_Add(ref s4PLCWriteData, "d5VehicleScanCode", writeToPLC_Flag);
  3579. stopwatch2.Stop();
  3580. }
  3581. stopwatch1.Stop();
  3582. AddMessage(LogType.Info, stationNameStr + "_载具扫码;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  3583. }
  3584. // 上次采集到的SN
  3585. //private string sn_S4_5出站接口 = string.Empty;
  3586. /// <summary>
  3587. /// [S4] 取放桁架 - S4_5出站接口
  3588. /// </summary>
  3589. private void S4_5出站接口(int plcNo, string stationCode, string stationName)
  3590. {
  3591. Stopwatch stopwatch1 = new Stopwatch();
  3592. Stopwatch stopwatch2 = new Stopwatch();
  3593. string equipmentCode = GlobalContext.LineCode + "-" + stationCode; // 设备编号
  3594. string stationNameStr = stationCode + stationName;
  3595. string processItem = stationName; // 测试项目
  3596. try
  3597. {
  3598. stopwatch1.Start();
  3599. string workorder_code = GlobalContext.WorkOrderCode; // 工单号
  3600. string batch_num = GlobalContext.BatchNumber; // 批次号
  3601. string mtltmrk = GlobalContext.Mtltmrk; // 产品型号
  3602. string plcDate_YMD = DateTime.Now.ToString("yyyyMMdd");
  3603. string supplierCode = ""; // 供应商代码
  3604. string sn = (string)s4PLCData["d5ProductSN"]; // 产品SN(弹夹码)
  3605. sn = sn.Replace("\0", "");
  3606. string d5VehicleCode1 = (string)s4PLCData["d5VehicleCode1"]; // 载具1码(弹夹穴位1)
  3607. string d5VehicleCode2 = (string)s4PLCData["d5VehicleCode2"]; // 载具2码(弹夹穴位2)
  3608. string d5VehicleCode3 = (string)s4PLCData["d5VehicleCode3"]; // 载具3码(弹夹穴位3)
  3609. string d5VehicleCode4 = (string)s4PLCData["d5VehicleCode4"]; // 载具4码(弹夹穴位4)
  3610. string d5VehicleCode5 = (string)s4PLCData["d5VehicleCode5"]; // 载具5码(弹夹穴位5)
  3611. string d5VehicleCode6 = (string)s4PLCData["d5VehicleCode6"]; // 载具6码(弹夹穴位6)
  3612. string d5VehicleCode7 = (string)s4PLCData["d5VehicleCode7"]; // 载具7码(弹夹穴位7)
  3613. string d5VehicleCode8 = (string)s4PLCData["d5VehicleCode8"]; // 载具8码(弹夹穴位8)
  3614. string d5VehicleCode9 = (string)s4PLCData["d5VehicleCode9"]; // 载具9码(弹夹穴位9)
  3615. string d5VehicleCode10 = (string)s4PLCData["d5VehicleCode10"]; // 载具10码(弹夹穴位10)
  3616. string d5VehicleCode11 = (string)s4PLCData["d5VehicleCode11"]; // 载具11码(弹夹穴位11)
  3617. string d5VehicleCode12 = (string)s4PLCData["d5VehicleCode12"]; // 载具12码(弹夹穴位12)
  3618. string d5VehicleCode13 = (string)s4PLCData["d5VehicleCode13"]; // 载具13码(弹夹穴位13)
  3619. string d5VehicleCode14 = (string)s4PLCData["d5VehicleCode14"]; // 载具14码(弹夹穴位14)
  3620. string d5VehicleCode15 = (string)s4PLCData["d5VehicleCode15"]; // 载具15码(弹夹穴位15)
  3621. int d5Result = (int)s4PLCData["d5Result"]; // 产品结果
  3622. bool pass = d5Result == 1;
  3623. List<TestItem> items1 = new List<TestItem>();
  3624. items1.Add(new TestItem()
  3625. {
  3626. Parameter_name = "产品结果",
  3627. Parameter_value = d5Result == 1 ? "OK" : "NG",
  3628. Parameter_unit = ""
  3629. });
  3630. int result1 = SwitctProcessData(stationNameStr, items1, equipmentCode, processItem
  3631. , workorder_code, batch_num, mtltmrk, plcDate_YMD, supplierCode, sn, pass, d5VehicleCode1, "1");
  3632. //int result = result1 == 1 ? 1 : (GlobalContext.IsSendProcessData ? 4 : 1);
  3633. short result = result1 == 1 ? (short)1 : (short)3;
  3634. stopwatch2.Start();
  3635. // MES_Flag 为4MES报错
  3636. //Funs[plcNo].WriteMultipleRegisters<short>(2591, result); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  3637. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  3638. writeToPLC_Flag.Name = "d5MES_FLAG";
  3639. writeToPLC_Flag.Adress = 2591;
  3640. writeToPLC_Flag.Value = result;
  3641. SxPLCWriteData_Add(ref s4PLCWriteData, "d5MES_FLAG", writeToPLC_Flag);
  3642. stopwatch2.Stop();
  3643. WritePLCLog(LogType.Debug, $"PLC{plcNo}_[{equipmentCode}]{processItem}-Write" + (result == 1 ? "成功!" : "失败!"));
  3644. }
  3645. catch (Exception ex)
  3646. {
  3647. stopwatch2.Start();
  3648. // MES_Flag 为4上位机报错
  3649. //Funs[plcNo].WriteMultipleRegisters<short>(2591, (short)4); // 4代表上位机报警
  3650. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  3651. writeToPLC_Flag.Name = "d5MES_FLAG";
  3652. writeToPLC_Flag.Adress = 2591;
  3653. writeToPLC_Flag.Value = (short)4;
  3654. SxPLCWriteData_Add(ref s4PLCWriteData, "d5MES_FLAG", writeToPLC_Flag);
  3655. stopwatch2.Stop();
  3656. string str = ex.StackTrace;
  3657. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_[{equipmentCode}]{processItem}上传出站接口!错误信息:" + ex.Message.ToString() + ";异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  3658. }
  3659. stopwatch1.Stop();
  3660. AddMessage(LogType.Info, stationNameStr + "_出站接口;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  3661. }
  3662. /// <summary>
  3663. /// [S4] 取放桁架 - S4_5节拍接口
  3664. /// </summary>
  3665. /// <param name="plcNo">PLC编号</param>
  3666. /// <param name="stationNameStr">工站全称</param>
  3667. private void S4_5节拍接口(int plcNo, string stationNameStr)
  3668. {
  3669. Stopwatch stopwatch1 = new Stopwatch();
  3670. Stopwatch stopwatch2 = new Stopwatch();
  3671. string resultStr = string.Empty;
  3672. try
  3673. {
  3674. stopwatch1.Start();
  3675. string oEEType = ((int)s4PLCData["d5OEEType"]).ToString(); // 节拍类型(plc写入)
  3676. string d5OEEProductSN = (string)s4PLCData["d5OEEProductSN"]; // 载具SN
  3677. d5OEEProductSN = d5OEEProductSN.Replace("\0", "");
  3678. bool actionBool = Enum.TryParse(oEEType, out XiaomiDeviceOEE deviceOEE);
  3679. if (!actionBool)
  3680. {
  3681. stopwatch2.Start();
  3682. // MES_Flag
  3683. //Funs[plcNo].WriteMultipleRegisters<short>(2924, (short)4); // 上位机;发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警
  3684. WriteToPLC_Flag writeToPLC_Flag1 = new WriteToPLC_Flag(); // MES_Flag
  3685. writeToPLC_Flag1.Name = "d5OEEMES_FLAG";
  3686. writeToPLC_Flag1.Adress = 2924;
  3687. writeToPLC_Flag1.Value = (short)4;
  3688. SxPLCWriteData_Add(ref s4PLCWriteData, "d5OEEMES_FLAG", writeToPLC_Flag1);
  3689. stopwatch2.Stop();
  3690. AddMessage(LogType.Info, stationNameStr + $"_节拍接口-- 设备上传了未识别的节拍类型【{oEEType}】请检查;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  3691. return;
  3692. }
  3693. string d5OEEPartNo = string.Empty; // 物料码
  3694. if (string.IsNullOrEmpty(d5OEEProductSN))
  3695. {
  3696. stopwatch2.Start();
  3697. // MES_Flag
  3698. //Funs[plcNo].WriteMultipleRegisters<short>(2924, (short)1); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  3699. WriteToPLC_Flag writeToPLC_Flag1 = new WriteToPLC_Flag(); // MES_Flag
  3700. writeToPLC_Flag1.Name = "d5OEEMES_FLAG";
  3701. writeToPLC_Flag1.Adress = 2924;
  3702. writeToPLC_Flag1.Value = (short)1;
  3703. SxPLCWriteData_Add(ref s4PLCWriteData, "d5OEEMES_FLAG", writeToPLC_Flag1);
  3704. stopwatch2.Stop();
  3705. AddMessage(LogType.Info, stationNameStr + $"_节拍接口-- 上传内容无效已自动省略;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  3706. return;
  3707. }
  3708. else
  3709. { // 查产品SN
  3710. d5OEEPartNo = "Test"; // ZS
  3711. }
  3712. short d5OEEMES_FLAG = 0;
  3713. // 上传OEE
  3714. (short, string) result = SaveOEEData(plcNo, stationNameStr, deviceOEE, d5OEEPartNo, d5OEEProductSN);
  3715. d5OEEMES_FLAG = result.Item1;
  3716. resultStr = result.Item2;
  3717. stopwatch2.Start();
  3718. // MES_Flag
  3719. //Funs[plcNo].WriteMultipleRegisters<short>(2924, d5OEEMES_FLAG); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  3720. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  3721. writeToPLC_Flag.Name = "d5OEEMES_FLAG";
  3722. writeToPLC_Flag.Adress = 2924;
  3723. writeToPLC_Flag.Value = d5OEEMES_FLAG;
  3724. SxPLCWriteData_Add(ref s4PLCWriteData, "d5OEEMES_FLAG", writeToPLC_Flag);
  3725. stopwatch2.Stop();
  3726. }
  3727. catch (Exception ex)
  3728. {
  3729. string str = ex.StackTrace;
  3730. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 节拍接口出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  3731. // MES_Flag
  3732. stopwatch2.Start();
  3733. //Funs[plcNo].WriteMultipleRegisters<short>(2924, (short)4); // 4代表上位机报警
  3734. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  3735. writeToPLC_Flag.Name = "d5OEEMES_FLAG";
  3736. writeToPLC_Flag.Adress = 2924;
  3737. writeToPLC_Flag.Value = (short)4;
  3738. SxPLCWriteData_Add(ref s4PLCWriteData, "d5OEEMES_FLAG", writeToPLC_Flag);
  3739. stopwatch2.Stop();
  3740. }
  3741. stopwatch1.Stop();
  3742. AddMessage(LogType.Info, stationNameStr + $"_节拍接口-- {resultStr};总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  3743. }
  3744. #endregion [S4] 取放桁架
  3745. #endregion PLC4 刘果段
  3746. #region PLC5 张超凡
  3747. #region [S5] Tray盘下料装备
  3748. /// <summary>
  3749. /// S5工位的数据- 触发信号上次的值
  3750. /// </summary>
  3751. private Dictionary<string, object> s5PLCSignal_Old = new Dictionary<string, object>();
  3752. /// <summary>
  3753. /// S5工位的数据(含触发信号)
  3754. /// </summary>
  3755. private Dictionary<string, object> s5PLCData = new Dictionary<string, object>();
  3756. /// <summary>
  3757. /// S5工位的数据- 回写点位
  3758. /// </summary>
  3759. private Dictionary<string, WriteToPLC_Flag> s5PLCWriteData = new Dictionary<string, WriteToPLC_Flag>();
  3760. /// <summary>
  3761. /// [S5] Tray盘下料装备
  3762. /// </summary>
  3763. /// <param name="plcNo">PLC编号</param>
  3764. private void ReadStation_S5(int plcNo)
  3765. {
  3766. // [S1] Tray盘上料装备
  3767. // [S2] FCT
  3768. // [S3] 值板机
  3769. // [S4_1] 载具下线装备 [S4_5] 载具上线装备
  3770. // [S5] Tray盘下料装备
  3771. /// 上位机心跳
  3772. /// 获取设备报警数据与状态信息
  3773. string stationCode = "[S5]";
  3774. string stationName = "Tray盘下料装备";
  3775. string stationNameStr = stationCode + stationName;
  3776. #region 创建字典
  3777. // 触发信号字典 赋值
  3778. s5PLCSignal_Old.Add("e1PLC_FLAG_Check", 0); // PLC_FLAG 进站校验
  3779. s5PLCSignal_Old.Add("e1PLC_FLAG", 0); // PLC_FLAG 出站接口
  3780. s5PLCSignal_Old.Add("e1OEEPLC_FLAG", 0); // PLC_FLAG 节拍接口
  3781. s5PLCSignal_Old.Add("e1AGVUpCall", 0); // AGV上料叫agv信号 AGV上料
  3782. s5PLCSignal_Old.Add("e1AGVUpEnd", 0); // AGV上料完成信号 AGV上料
  3783. s5PLCSignal_Old.Add("e1AGVDownCall", 0); // AGV下料叫agv信号 AGV下料
  3784. s5PLCSignal_Old.Add("e1AGVDownEnd", 0); // AGV下料完成信号 AGV下料
  3785. // PLC数据字典 赋值
  3786. s5PLCData.Add("e1PLC_FLAG_Check", 0); // PLC_FLAG 进站校验
  3787. s5PLCData.Add("e1MES_FLAG_Check", 0); // MES_FLAG
  3788. s5PLCData.Add("e1ProductSN_Check", ""); //
  3789. s5PLCData.Add("e1PLC_FLAG", 0); // PLC_FLAG 出站接口
  3790. s5PLCData.Add("e1MES_FLAG", 0); // MES_FLAG
  3791. s5PLCData.Add("e1ProductSN", ""); // 产品SN
  3792. s5PLCData.Add("e1PartNo", ""); // 物料码
  3793. s5PLCData.Add("e1Result", 0); // 产品结果
  3794. s5PLCData.Add("e1OEEPLC_FLAG", 0); // PLC_FLAG 节拍接口
  3795. s5PLCData.Add("e1OEEMES_FLAG", 0); // MES_FLAG
  3796. s5PLCData.Add("e1OEEProductSN", "");// 产品SN(载具SN)
  3797. s5PLCData.Add("e1OEEType", 0); // 节拍类型(plc写入)
  3798. s5PLCData.Add("e1AGVUpCall", 0); // AGV上料叫agv信号 AGV上料
  3799. s5PLCData.Add("e1AGVUpStart", 0); // AGV上料开始信号
  3800. s5PLCData.Add("e1AGVUpEnd", 0); // AGV上料完成信号
  3801. s5PLCData.Add("e1AGVDownCall", 0); // AGV下料叫agv信号 AGV下料
  3802. s5PLCData.Add("e1AGVDownStart", 0); // AGV下料开始信号
  3803. s5PLCData.Add("e1AGVDownEnd", 0); // AGV下料完成信号
  3804. #endregion 创建字典
  3805. while (true)
  3806. {
  3807. try
  3808. {
  3809. if (!GlobalContext._IsCon_Funs5)
  3810. {
  3811. UpdatePLCMonitor(1, plcNo, 0);
  3812. continue;
  3813. }
  3814. if (Funs[plcNo].IsConnected) // 检查PLC是否已连接上
  3815. {
  3816. Stopwatch stopwatch1 = new Stopwatch();
  3817. Stopwatch stopwatch2 = new Stopwatch();
  3818. stopwatch1.Start();
  3819. /*
  3820. stopwatch2.Start();
  3821. #region 一次性读取所有数据
  3822. int[] data1 = Funs[plcNo].ReadHoldingRegisters(2000, 100);
  3823. int[] data2 = Funs[plcNo].ReadHoldingRegisters(2100, 46);
  3824. int[] datas = data1.Concat(data2).ToArray();
  3825. s5PLCData["e1PLC_FLAG_Check"] = datas[2]; // 进站校验
  3826. s5PLCData["e1MES_FLAG_Check"] = datas[3];
  3827. int[] e1ProductSN_CheckData = datas.Skip(4).Take(20).ToArray();
  3828. s5PLCData["e1ProductSN_Check"] = ModbusClient.ConvertRegistersToString(e1ProductSN_CheckData, 0, 40);
  3829. s5PLCData["e1PLC_FLAG"] = datas[34]; // 出站接口
  3830. s5PLCData["e1MES_FLAG"] = datas[35];
  3831. int[] e1ProductSNData = datas.Skip(36).Take(20).ToArray();
  3832. s5PLCData["e1ProductSN"] = ModbusClient.ConvertRegistersToString(e1ProductSNData, 0, 40);
  3833. int[] e1PartNoData = datas.Skip(56).Take(20).ToArray();
  3834. s5PLCData["e1PartNo"] = ModbusClient.ConvertRegistersToString(e1PartNoData, 0, 40);
  3835. s5PLCData["e1Result"] = datas[76];
  3836. s5PLCData["e1OEEPLC_FLAG"] = datas[87]; // 节拍接口
  3837. s5PLCData["e1OEEMES_FLAG"] = datas[88];
  3838. int[] e1OEEProductSNData = datas.Skip(89).Take(20).ToArray();
  3839. s5PLCData["e1OEEProductSN"] = ModbusClient.ConvertRegistersToString(e1OEEProductSNData, 0, 40);
  3840. s5PLCData["e1OEEType"] = datas[109];
  3841. s5PLCData["e1AGVUpCall"] = datas[120]; // AGV上料
  3842. s5PLCData["e1AGVUpStart"] = datas[121];
  3843. s5PLCData["e1AGVUpEnd"] = datas[122];
  3844. s5PLCData["e1AGVDownCall"] = datas[133]; // AGV下料
  3845. s5PLCData["e1AGVDownStart"] = datas[134];
  3846. s5PLCData["e1AGVDownEnd"] = datas[135];
  3847. #endregion 一次性读取所有数据
  3848. stopwatch2.Stop();
  3849. #region 回写操作,写后清空flag
  3850. PLCWriteData(Funs[plcNo], ref s5PLCData, ref s5PLCWriteData);
  3851. #endregion 回写操作,写后清空flag
  3852. #region 进站校验
  3853. try
  3854. {
  3855. int e1PLC_FLAG_Check = (int)s5PLCData["e1PLC_FLAG_Check"];
  3856. int e1MES_FLAG_Check = (int)s5PLCData["e1MES_FLAG_Check"];
  3857. int e1PLC_FLAG_CheckOld = (int)s5PLCSignal_Old["e1PLC_FLAG_Check"];
  3858. if (e1PLC_FLAG_Check != e1PLC_FLAG_CheckOld)
  3859. {
  3860. if (e1PLC_FLAG_Check == 1 && e1MES_FLAG_Check == 0) // 0->1
  3861. Task.Run(() => S5进站校验(plcNo, stationNameStr)); // MreTasks[2].Set();
  3862. else if (e1PLC_FLAG_Check == 0 && e1MES_FLAG_Check != 0)
  3863. Funs[plcNo].WriteMultipleRegisters<short>(2003, (short)0);
  3864. s5PLCSignal_Old["e1PLC_FLAG_Check"] = s5PLCData["e1PLC_FLAG_Check"];
  3865. }
  3866. }
  3867. catch (Exception ex)
  3868. {
  3869. Funs[plcNo].WriteMultipleRegisters<short>(2003, (short)6); // 6代表上位机报警
  3870. string str = ex.StackTrace;
  3871. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 进站校验出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  3872. }
  3873. #endregion 进站校验
  3874. */
  3875. #region 出站接口
  3876. try
  3877. {
  3878. int e1PLC_FLAG = (int)s5PLCData["e1PLC_FLAG"];
  3879. int e1MES_FLAG = (int)s5PLCData["e1MES_FLAG"];
  3880. int e1PLC_FLAGOld = (int)s5PLCSignal_Old["e1PLC_FLAG"];
  3881. if (e1PLC_FLAG != e1PLC_FLAGOld)
  3882. {
  3883. if (e1PLC_FLAG == 1 && e1MES_FLAG == 0) // 0->1
  3884. Task.Run(() => S5出站接口(plcNo, stationCode, stationName)); // MreTasks[3].Set();
  3885. //else if (e1PLC_FLAG == 0 && e1MES_FLAG != 0)
  3886. //Funs[plcNo].WriteMultipleRegisters<short>(2035, (short)0);
  3887. s5PLCSignal_Old["e1PLC_FLAG"] = s5PLCData["e1PLC_FLAG"];
  3888. }
  3889. }
  3890. catch (Exception ex)
  3891. {
  3892. //Funs[plcNo].WriteMultipleRegisters<short>(2035, (short)6); // 6代表上位机报警
  3893. string str = ex.StackTrace;
  3894. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 上传出站接口出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  3895. }
  3896. #endregion 出站接口
  3897. #region 节拍接口
  3898. try
  3899. {
  3900. int e1OEEPLC_FLAG = (int)s5PLCData["e1OEEPLC_FLAG"];
  3901. int e1OEEMES_FLAG = (int)s5PLCData["e1OEEMES_FLAG"];
  3902. int e1OEEPLC_FLAGOld = (int)s5PLCSignal_Old["e1OEEPLC_FLAG"];
  3903. if (e1OEEPLC_FLAG != e1OEEPLC_FLAGOld)
  3904. {
  3905. if (e1OEEPLC_FLAG == 1 && e1OEEMES_FLAG == 0) // 0->1
  3906. Task.Run(() => S5节拍接口(plcNo, stationNameStr)); // MreTasks[4].Set();
  3907. //else if (e1OEEPLC_FLAG == 0 && e1OEEMES_FLAG != 0)
  3908. //Funs[plcNo].WriteMultipleRegisters<short>(2088, (short)0);
  3909. s5PLCSignal_Old["e1OEEPLC_FLAG"] = s5PLCData["e1OEEPLC_FLAG"];
  3910. }
  3911. }
  3912. catch (Exception ex)
  3913. {
  3914. //Funs[plcNo].WriteMultipleRegisters<short>(2088, (short)4); // 4代表上位机报警
  3915. string str = ex.StackTrace;
  3916. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 上传节拍接口出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  3917. }
  3918. #endregion 节拍接口
  3919. #region AGV上料
  3920. // AGV上料叫AGV信号
  3921. try
  3922. {
  3923. int e1AGVUpCall = (int)s5PLCData["e1AGVUpCall"];
  3924. int e1AGVUpCallOld = (int)s5PLCSignal_Old["e1AGVUpCall"];
  3925. if (e1AGVUpCall != e1AGVUpCallOld)
  3926. {
  3927. if (e1AGVUpCall == 1) // 0->1
  3928. Task.Run(() => S5AGV上料叫agv(plcNo, stationNameStr)); // MreTasks[5].Set();
  3929. s5PLCSignal_Old["e1AGVUpCall"] = s5PLCData["e1AGVUpCall"];
  3930. }
  3931. }
  3932. catch (Exception ex)
  3933. {
  3934. //Funs[plcNo].WriteMultipleRegisters<short>(2120, (short)4); // 4代表上位机报警
  3935. string str = ex.StackTrace;
  3936. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} AGV上料叫agv出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  3937. }
  3938. // AGV上料完成信号
  3939. try
  3940. {
  3941. int e1AGVUpEnd = (int)s5PLCData["e1AGVUpEnd"];
  3942. int e1AGVUpEndOld = (int)s5PLCSignal_Old["e1AGVUpEnd"];
  3943. if (e1AGVUpEnd != e1AGVUpEndOld)
  3944. {
  3945. if (e1AGVUpEnd == 1) // 0->1
  3946. Task.Run(() => S5AGV上料完成(plcNo, stationNameStr)); // MreTasks[6].Set();
  3947. s5PLCSignal_Old["e1AGVUpEnd"] = s5PLCData["e1AGVUpEnd"];
  3948. }
  3949. }
  3950. catch (Exception ex)
  3951. {
  3952. //Funs[plcNo].WriteMultipleRegisters<short>(2122, (short)4); // 4代表上位机报警
  3953. string str = ex.StackTrace;
  3954. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} AGV上料完成信号出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  3955. }
  3956. #endregion AGV上料
  3957. #region AGV下料
  3958. // AGV下料叫agv信号
  3959. try
  3960. {
  3961. int e1AGVDownCall = (int)s5PLCData["e1AGVDownCall"];
  3962. int e1AGVDownCallOld = (int)s5PLCSignal_Old["e1AGVDownCall"];
  3963. if (e1AGVDownCall != e1AGVDownCallOld)
  3964. {
  3965. if (e1AGVDownCall == 1) // 0->1
  3966. Task.Run(() => S5AGV下料叫agv(plcNo, stationNameStr)); // MreTasks[7].Set();
  3967. s5PLCSignal_Old["e1AGVDownCall"] = s5PLCData["e1AGVDownCall"];
  3968. }
  3969. }
  3970. catch (Exception ex)
  3971. {
  3972. //Funs[plcNo].WriteMultipleRegisters<short>(2133, (short)4); // 4代表上位机报警
  3973. string str = ex.StackTrace;
  3974. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} AGV下料叫agv信号出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  3975. }
  3976. // AGV下料完成信号
  3977. try
  3978. {
  3979. int e1AGVDownEnd = (int)s5PLCData["e1AGVDownEnd"];
  3980. int e1AGVDownEndOld = (int)s5PLCSignal_Old["e1AGVDownEnd"];
  3981. if (e1AGVDownEnd != e1AGVDownEndOld)
  3982. {
  3983. if (e1AGVDownEnd == 1) // 0->1
  3984. Task.Run(() => S5AGV下料完成(plcNo, stationNameStr)); // MreTasks[8].Set();
  3985. s5PLCSignal_Old["e1AGVDownEnd"] = s5PLCData["e1AGVDownEnd"];
  3986. }
  3987. }
  3988. catch (Exception ex)
  3989. {
  3990. // Funs[plcNo].WriteMultipleRegisters<short>(2135, (short)4); // 4代表上位机报警
  3991. string str = ex.StackTrace;
  3992. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} AGV下料完成信号出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  3993. }
  3994. #endregion AGV下料
  3995. UpdatePLCMonitor(1, plcNo, 1); // 更新PLC状态的UI // 更新PLC状态的UI
  3996. stopwatch1.Stop();
  3997. //if (stopwatch1.ElapsedMilliseconds > 60) // ZS 稳定后取消注释该项
  3998. OnMessage(LogType.Info, $"循环读取PLC数据一次,总用时{stopwatch1.ElapsedMilliseconds}ms[读取用时{stopwatch2.ElapsedMilliseconds}ms]");
  3999. }
  4000. else
  4001. {
  4002. UpdatePLCMonitor(1, plcNo, 0); // 更新PLC状态的UI
  4003. AddMessage_Station(stationNameStr, LogType.Info, "PLC" + plcNo.ToString() + "_" + stationNameStr + "连接失败!");
  4004. Funs[plcNo].Connect();
  4005. }
  4006. }
  4007. catch (Exception ex)
  4008. {
  4009. UpdatePLCMonitor(1, plcNo, 0); // 更新PLC状态的UI
  4010. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr}运行出错!错误信息:" + ex.Message.ToString());
  4011. //Funs[plcNo].ReConnect();
  4012. }
  4013. Thread.Sleep(IntervalReadPLC);
  4014. }
  4015. }
  4016. /// <summary>
  4017. /// [S5] Tray盘下料装备 - 进站校验
  4018. /// </summary>
  4019. /// <param name="plcNo">PLC编号</param>
  4020. /// <param name="stationNameStr">工站全称</param>
  4021. private void S5进站校验(int plcNo, string stationNameStr)
  4022. {
  4023. Stopwatch stopwatch1 = new Stopwatch();
  4024. Stopwatch stopwatch2 = new Stopwatch();
  4025. try
  4026. {
  4027. stopwatch1.Start();
  4028. string sn = (string)s5PLCData["e1ProductSN_Check"]; // 产品SN(载具码)
  4029. sn = sn.Replace("\0", "");
  4030. // 获取产品SN By 载具码
  4031. string partNo = string.Empty;
  4032. // 产品SN(物料码)校验
  4033. List<TestItem> item = new List<TestItem>();
  4034. item.Add(new TestItem()
  4035. {
  4036. Parameter_name = "载具码",
  4037. Parameter_value = sn,
  4038. });
  4039. item.Add(new TestItem()
  4040. {
  4041. Parameter_name = "载具穴号",
  4042. Parameter_value = "1",
  4043. });
  4044. stopwatch2.Start();
  4045. int result = SaveStationInData(stationNameStr, GlobalContext.WorkOrderCode, GlobalContext.Mtltmrk, partNo, item);
  4046. stopwatch2.Stop();
  4047. short e1MES_FLAG_Check = (short)result;
  4048. // MES_Flag
  4049. //Funs[plcNo].WriteMultipleRegisters<short>(2003, e1MES_FLAG_Check); // 上位机发送1代表OK可以进站;2代表不需要进站;3代表本站返修料;5客户MES报警;6代表上位机报警
  4050. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  4051. writeToPLC_Flag.Name = "e1MES_FLAG_Check";
  4052. writeToPLC_Flag.Adress = 2003;
  4053. writeToPLC_Flag.Value = e1MES_FLAG_Check;
  4054. SxPLCWriteData_Add(ref s5PLCWriteData, "e1MES_FLAG_Check", writeToPLC_Flag);
  4055. }
  4056. catch (Exception ex)
  4057. {
  4058. string str = ex.StackTrace;
  4059. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 进站校验出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  4060. // MES_Flag
  4061. //Funs[plcNo].WriteMultipleRegisters<short>(2003, (short)6); // 6代表上位机报警
  4062. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  4063. writeToPLC_Flag.Name = "e1MES_FLAG_Check";
  4064. writeToPLC_Flag.Adress = 2003;
  4065. writeToPLC_Flag.Value = (short)6;
  4066. SxPLCWriteData_Add(ref s5PLCWriteData, "e1MES_FLAG_Check", writeToPLC_Flag);
  4067. }
  4068. stopwatch1.Stop();
  4069. AddMessage(LogType.Info, stationNameStr + "_进站校验;总用时" + stopwatch1.ElapsedMilliseconds + "ms;调用MES用时" + stopwatch2.ElapsedMilliseconds + "ms");
  4070. }
  4071. /// <summary>
  4072. /// [S5] Tray盘下料装备 - 出站接口
  4073. /// </summary>
  4074. /// <param name="plcNo"></param>
  4075. /// <param name="stationCode"></param>
  4076. /// <param name="stationName"></param>
  4077. private void S5出站接口(int plcNo, string stationCode, string stationName)
  4078. {
  4079. Stopwatch stopwatch1 = new Stopwatch();
  4080. Stopwatch stopwatch2 = new Stopwatch();
  4081. string equipmentCode = GlobalContext.LineCode + "-" + stationCode; // 设备编号
  4082. string stationNameStr = stationCode + stationName;
  4083. string processItem = stationName; // 测试项目
  4084. try
  4085. {
  4086. stopwatch1.Start();
  4087. string workorder_code = GlobalContext.WorkOrderCode; // 工单号
  4088. string batch_num = GlobalContext.BatchNumber; // 批次号
  4089. string mtltmrk = GlobalContext.Mtltmrk; // 产品型号
  4090. string plcDate_YMD = DateTime.Now.ToString("yyyyMMdd");
  4091. string supplierCode = ""; // 供应商代码
  4092. string sn = (string)s5PLCData["e1ProductSN"]; // 产品SN(载具SN码)
  4093. sn = sn.Replace("\0", "");
  4094. //string partNo = (string)s5PLCData["e1PartNo"]; // 物料码
  4095. //partNo = partNo.Replace("\0", "");
  4096. string partNo = string.Empty;
  4097. int e1Result = (int)s5PLCData["e1Result"]; // 产品结果
  4098. bool pass = e1Result == 1;
  4099. List<TestItem> items = new List<TestItem>();
  4100. items.Add(new TestItem()
  4101. {
  4102. Parameter_name = "载具码",
  4103. Parameter_value = sn,
  4104. Parameter_unit = ""
  4105. });
  4106. items.Add(new TestItem()
  4107. {
  4108. Parameter_name = "产品码",
  4109. Parameter_value = partNo,
  4110. Parameter_unit = ""
  4111. });
  4112. int result1 = SwitctProcessData(stationNameStr, items, equipmentCode, processItem
  4113. , workorder_code, batch_num, mtltmrk, plcDate_YMD, supplierCode, partNo, pass, sn, "1");
  4114. //int result = result1 == 1 ? 1 : (GlobalContext.IsSendProcessData ? 4 : 1);
  4115. short result = result1 == 1 ? (short)1 : (short)3;
  4116. stopwatch2.Start();
  4117. // MES_Flag 为MES报错
  4118. // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  4119. //Funs[plcNo].WriteMultipleRegisters<short>(2035, result); // 4代表上位机报警
  4120. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  4121. writeToPLC_Flag.Name = "e1MES_FLAG";
  4122. writeToPLC_Flag.Adress = 2035;
  4123. writeToPLC_Flag.Value = result;
  4124. SxPLCWriteData_Add(ref s5PLCWriteData, "e1MES_FLAG", writeToPLC_Flag);
  4125. stopwatch2.Stop();
  4126. WritePLCLog(LogType.Debug, $"PLC{plcNo}_[{equipmentCode}]{processItem}-Write" + (result == 1 ? "成功!" : "失败!"));
  4127. }
  4128. catch (Exception ex)
  4129. {
  4130. stopwatch2.Start();
  4131. // MES_Flag 为4上位机报错
  4132. //Funs[plcNo].WriteMultipleRegisters<short>(2035, (short)4); // 4代表上位机报警
  4133. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  4134. writeToPLC_Flag.Name = "e1MES_FLAG";
  4135. writeToPLC_Flag.Adress = 2035;
  4136. writeToPLC_Flag.Value = (short)4;
  4137. SxPLCWriteData_Add(ref s5PLCWriteData, "e1MES_FLAG", writeToPLC_Flag);
  4138. stopwatch2.Stop();
  4139. string str = ex.StackTrace;
  4140. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_[{equipmentCode}]{processItem}上传出站接口报错!错误信息:" + ex.Message.ToString() + ";异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  4141. }
  4142. stopwatch1.Stop();
  4143. AddMessage(LogType.Info, stationNameStr + "_出站接口;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  4144. }
  4145. /// <summary>
  4146. /// [S5] Tray盘下料装备 - 节拍接口
  4147. /// </summary>
  4148. /// <param name="plcNo">PLC编号</param>
  4149. /// <param name="stationNameStr">工站全称</param>
  4150. private void S5节拍接口(int plcNo, string stationNameStr)
  4151. {
  4152. Stopwatch stopwatch1 = new Stopwatch();
  4153. Stopwatch stopwatch2 = new Stopwatch();
  4154. string resultStr = string.Empty;
  4155. try
  4156. {
  4157. stopwatch1.Start();
  4158. string oEEType = ((int)s5PLCData["e1OEEType"]).ToString(); // 节拍类型(plc写入)
  4159. string e1OEEProductSN = (string)s5PLCData["e1OEEProductSN"]; // 载具SN
  4160. e1OEEProductSN = e1OEEProductSN.Replace("\0", "");
  4161. bool actionBool = Enum.TryParse(oEEType, out XiaomiDeviceOEE deviceOEE);
  4162. if (!actionBool)
  4163. {
  4164. stopwatch2.Start();
  4165. // MES_Flag
  4166. //Funs[plcNo].WriteMultipleRegisters<short>(2088, (short)4); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  4167. WriteToPLC_Flag writeToPLC_Flag1 = new WriteToPLC_Flag(); // MES_Flag
  4168. writeToPLC_Flag1.Name = "e1OEEMES_FLAG";
  4169. writeToPLC_Flag1.Adress = 2088;
  4170. writeToPLC_Flag1.Value = (short)4;
  4171. SxPLCWriteData_Add(ref s5PLCWriteData, "e1OEEMES_FLAG", writeToPLC_Flag1);
  4172. stopwatch2.Stop();
  4173. AddMessage(LogType.Info, stationNameStr + $"_节拍接口-- 设备上传了未识别的节拍类型【{oEEType}】请检查;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  4174. return;
  4175. }
  4176. string e1OEEPartNo = string.Empty; // 物料码
  4177. if (string.IsNullOrEmpty(e1OEEProductSN))
  4178. {
  4179. stopwatch2.Start();
  4180. // MES_Flag
  4181. //Funs[plcNo].WriteMultipleRegisters<short>(2088, (short)1); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  4182. WriteToPLC_Flag writeToPLC_Flag1 = new WriteToPLC_Flag(); // MES_Flag
  4183. writeToPLC_Flag1.Name = "e1OEEMES_FLAG";
  4184. writeToPLC_Flag1.Adress = 2088;
  4185. writeToPLC_Flag1.Value = (short)1;
  4186. SxPLCWriteData_Add(ref s5PLCWriteData, "e1OEEMES_FLAG", writeToPLC_Flag1);
  4187. stopwatch2.Stop();
  4188. AddMessage(LogType.Info, stationNameStr + $"_节拍接口-- 上传内容无效已自动省略;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  4189. return;
  4190. }
  4191. else
  4192. { // 查产品SN
  4193. e1OEEPartNo = "Test"; // ZS
  4194. }
  4195. short e1OEEMES_FLAG = 0;
  4196. // 上传OEE
  4197. (short, string) result = SaveOEEData(plcNo, stationNameStr, deviceOEE, e1OEEPartNo, e1OEEProductSN);
  4198. e1OEEMES_FLAG = result.Item1;
  4199. resultStr = result.Item2;
  4200. stopwatch2.Start();
  4201. // MES_Flag
  4202. //Funs[plcNo].WriteMultipleRegisters<short>(2088, e1OEEMES_FLAG); // 上位机发送1代表OK;2代表上传客户MES失败;3代表上位机保存数据失败;4代表上位机报警;
  4203. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  4204. writeToPLC_Flag.Name = "e1OEEMES_FLAG";
  4205. writeToPLC_Flag.Adress = 2088;
  4206. writeToPLC_Flag.Value = e1OEEMES_FLAG;
  4207. SxPLCWriteData_Add(ref s5PLCWriteData, "e1OEEMES_FLAG", writeToPLC_Flag);
  4208. stopwatch2.Stop();
  4209. }
  4210. catch (Exception ex)
  4211. {
  4212. string str = ex.StackTrace;
  4213. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} 节拍接口出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  4214. // MES_Flag
  4215. stopwatch2.Start();
  4216. //Funs[plcNo].WriteMultipleRegisters<short>(2088, (short)4); // 4代表上位机报警
  4217. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  4218. writeToPLC_Flag.Name = "e1OEEMES_FLAG";
  4219. writeToPLC_Flag.Adress = 2088;
  4220. writeToPLC_Flag.Value = (short)4;
  4221. SxPLCWriteData_Add(ref s5PLCWriteData, "e1OEEMES_FLAG", writeToPLC_Flag);
  4222. stopwatch2.Stop();
  4223. }
  4224. stopwatch1.Stop();
  4225. AddMessage(LogType.Info, stationNameStr + $"_节拍接口-- {resultStr};总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  4226. }
  4227. /// <summary>
  4228. /// [S5] Tray盘下料装备 - AGV上料叫agv
  4229. /// </summary>
  4230. /// <param name="plcNo">PLC编号</param>
  4231. /// <param name="stationNameStr">工站全称</param>
  4232. private void S5AGV上料叫agv(int plcNo, string stationNameStr)
  4233. {
  4234. Stopwatch stopwatch1 = new Stopwatch();
  4235. Stopwatch stopwatch2 = new Stopwatch();
  4236. try
  4237. {
  4238. stopwatch1.Start();
  4239. // ZS 呼叫AGV
  4240. short e1AGVUpCall = 2;
  4241. stopwatch2.Start();
  4242. // e1AGVUpCall
  4243. //Funs[plcNo].WriteMultipleRegisters<short>(2120, e1AGVUpCall); // 1:plc请求上料(plc请求);10秒响应清证明上位机掉线;2:调用成功(上位机返回);3:AGV报警(上位机返回);4:上位机报警(上位机返回);
  4244. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  4245. writeToPLC_Flag.Name = "e1AGVUpCall";
  4246. writeToPLC_Flag.Adress = 2120;
  4247. writeToPLC_Flag.Value = e1AGVUpCall;
  4248. SxPLCWriteData_Add(ref s5PLCWriteData, "e1AGVUpCall", writeToPLC_Flag);
  4249. stopwatch2.Stop();
  4250. }
  4251. catch (Exception ex)
  4252. {
  4253. string str = ex.StackTrace;
  4254. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} AGV上料叫agv出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  4255. // e1AGVUpCall
  4256. stopwatch2.Start();
  4257. //Funs[plcNo].WriteMultipleRegisters<short>(2120, (short)4); // 4代表上位机报警
  4258. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  4259. writeToPLC_Flag.Name = "e1AGVUpCall";
  4260. writeToPLC_Flag.Adress = 2120;
  4261. writeToPLC_Flag.Value = (short)4;
  4262. SxPLCWriteData_Add(ref s5PLCWriteData, "e1AGVUpCall", writeToPLC_Flag);
  4263. stopwatch2.Stop();
  4264. }
  4265. stopwatch1.Stop();
  4266. AddMessage(LogType.Info, stationNameStr + "_AGV上料叫agv;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  4267. }
  4268. /// <summary>
  4269. /// [S5] Tray盘下料装备 - AGV上料完成
  4270. /// </summary>
  4271. /// <param name="plcNo">PLC编号</param>
  4272. /// <param name="stationNameStr">工站全称</param>
  4273. private void S5AGV上料完成(int plcNo, string stationNameStr)
  4274. {
  4275. Stopwatch stopwatch1 = new Stopwatch();
  4276. Stopwatch stopwatch2 = new Stopwatch();
  4277. try
  4278. {
  4279. stopwatch1.Start();
  4280. // ZS AGV上料完成,让小车离开
  4281. short e1AGVUpEnd = 2;
  4282. stopwatch2.Start();
  4283. // e1AGVUpEnd
  4284. //Funs[plcNo].WriteMultipleRegisters<short>(2122, e1AGVUpEnd); // 1:plc通知完成结果(plc请求);2:调用成功(上位机返回);3:AGV报警(上位机返回);4:上位机报警(上位机返回);
  4285. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  4286. writeToPLC_Flag.Name = "e1AGVUpEnd";
  4287. writeToPLC_Flag.Adress = 2122;
  4288. writeToPLC_Flag.Value = e1AGVUpEnd;
  4289. SxPLCWriteData_Add(ref s5PLCWriteData, "e1AGVUpEnd", writeToPLC_Flag);
  4290. stopwatch2.Stop();
  4291. }
  4292. catch (Exception ex)
  4293. {
  4294. string str = ex.StackTrace;
  4295. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} AGV上料完成出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  4296. // e1AGVUpEnd
  4297. stopwatch2.Start();
  4298. //Funs[plcNo].WriteMultipleRegisters<short>(2122, (short)4); // 4代表上位机报警
  4299. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  4300. writeToPLC_Flag.Name = "e1AGVUpEnd";
  4301. writeToPLC_Flag.Adress = 2122;
  4302. writeToPLC_Flag.Value = (short)4;
  4303. SxPLCWriteData_Add(ref s5PLCWriteData, "e1AGVUpEnd", writeToPLC_Flag);
  4304. stopwatch2.Stop();
  4305. }
  4306. stopwatch1.Stop();
  4307. AddMessage(LogType.Info, stationNameStr + "_AGV上料完成;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  4308. }
  4309. /// <summary>
  4310. /// [S5] Tray盘下料装备 - AGV下料叫agv
  4311. /// </summary>
  4312. /// <param name="plcNo">PLC编号</param>
  4313. /// <param name="stationNameStr">工站全称</param>
  4314. private void S5AGV下料叫agv(int plcNo, string stationNameStr)
  4315. {
  4316. Stopwatch stopwatch1 = new Stopwatch();
  4317. Stopwatch stopwatch2 = new Stopwatch();
  4318. try
  4319. {
  4320. stopwatch1.Start();
  4321. // ZS 呼叫AGV
  4322. short e1AGVDownCall = 2;
  4323. stopwatch2.Start();
  4324. // e1AGVDownCall
  4325. //Funs[plcNo].WriteMultipleRegisters<short>(2133, e1AGVDownCall); // 1:plc请求下料(plc请求);10秒响应清证明上位机掉线;2:调用成功(上位机返回);3:AGV报警(上位机返回);4:上位机报警(上位机返回);
  4326. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  4327. writeToPLC_Flag.Name = "e1AGVDownCall";
  4328. writeToPLC_Flag.Adress = 2133;
  4329. writeToPLC_Flag.Value = e1AGVDownCall;
  4330. SxPLCWriteData_Add(ref s5PLCWriteData, "e1AGVDownCall", writeToPLC_Flag);
  4331. stopwatch2.Stop();
  4332. }
  4333. catch (Exception ex)
  4334. {
  4335. string str = ex.StackTrace;
  4336. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} AGV下料叫agv出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  4337. // e1AGVDownCall
  4338. stopwatch2.Start();
  4339. //Funs[plcNo].WriteMultipleRegisters<short>(2133, (short)4); // 4代表上位机报警
  4340. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  4341. writeToPLC_Flag.Name = "e1AGVDownCall";
  4342. writeToPLC_Flag.Adress = 2133;
  4343. writeToPLC_Flag.Value = (short)4;
  4344. SxPLCWriteData_Add(ref s5PLCWriteData, "e1AGVDownCall", writeToPLC_Flag);
  4345. stopwatch2.Stop();
  4346. }
  4347. stopwatch1.Stop();
  4348. AddMessage(LogType.Info, stationNameStr + "_AGV下料叫agv;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  4349. }
  4350. /// <summary>
  4351. /// [S5] Tray盘下料装备 - AGV下料完成
  4352. /// </summary>
  4353. /// <param name="plcNo">PLC编号</param>
  4354. /// <param name="stationNameStr">工站全称</param>
  4355. private void S5AGV下料完成(int plcNo, string stationNameStr)
  4356. {
  4357. Stopwatch stopwatch1 = new Stopwatch();
  4358. Stopwatch stopwatch2 = new Stopwatch();
  4359. try
  4360. {
  4361. stopwatch1.Start();
  4362. // ZS AGV上料完成,让小车离开
  4363. short e1AGVDownEnd = 2;
  4364. stopwatch2.Start();
  4365. // e1AGVDownEnd
  4366. //Funs[plcNo].WriteMultipleRegisters<short>(2135, e1AGVDownEnd); // 1:plc通知完成结果(plc请求);2:调用成功(上位机返回);3:AGV报警(上位机返回);4:上位机报警(上位机返回);
  4367. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  4368. writeToPLC_Flag.Name = "e1AGVDownEnd";
  4369. writeToPLC_Flag.Adress = 2135;
  4370. writeToPLC_Flag.Value = e1AGVDownEnd;
  4371. SxPLCWriteData_Add(ref s5PLCWriteData, "e1AGVDownEnd", writeToPLC_Flag);
  4372. stopwatch2.Stop();
  4373. }
  4374. catch (Exception ex)
  4375. {
  4376. string str = ex.StackTrace;
  4377. AddMessage_Station(stationNameStr, LogType.Error, $"PLC{plcNo}_{stationNameStr} AGV下料完成出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  4378. // e1AGVDownEnd
  4379. stopwatch2.Start();
  4380. //Funs[plcNo].WriteMultipleRegisters<short>(2135, (short)4); // 4代表上位机报警
  4381. WriteToPLC_Flag writeToPLC_Flag = new WriteToPLC_Flag(); // MES_Flag
  4382. writeToPLC_Flag.Name = "e1AGVDownEnd";
  4383. writeToPLC_Flag.Adress = 2135;
  4384. writeToPLC_Flag.Value = (short)4;
  4385. SxPLCWriteData_Add(ref s5PLCWriteData, "e1AGVDownEnd", writeToPLC_Flag);
  4386. stopwatch2.Stop();
  4387. }
  4388. stopwatch1.Stop();
  4389. AddMessage(LogType.Info, stationNameStr + "_AGV下料完成;总用时" + stopwatch1.ElapsedMilliseconds + "ms;写入用时" + stopwatch2.ElapsedMilliseconds + "ms");
  4390. }
  4391. #endregion [S5] Tray盘下料装备
  4392. #endregion PLC5 张超凡
  4393. #region 缓存读取到的PLC数据 与 需要写入的PLC数据
  4394. /// <summary>
  4395. /// PLC读取到的数据 -添加数据
  4396. /// </summary>
  4397. public static void SxPLCData_Add(ref Dictionary<string, object> sxPlcData, string newKey, object newValue)
  4398. {
  4399. if (sxPlcData.ContainsKey(newKey))
  4400. sxPlcData[newKey] = newValue;
  4401. else
  4402. sxPlcData.Add(newKey, newValue);
  4403. }
  4404. /// <summary>
  4405. /// PLC需要写入的数据 -添加数据
  4406. /// </summary>
  4407. public static void SxPLCWriteData_Add(ref Dictionary<string, WriteToPLC_Flag> sxPLCWriteData, string newKey, WriteToPLC_Flag newValue)
  4408. {
  4409. if (sxPLCWriteData.ContainsKey(newKey))
  4410. sxPLCWriteData[newKey] = newValue;
  4411. else
  4412. sxPLCWriteData.Add(newKey, newValue);
  4413. }
  4414. /// <summary>
  4415. /// PLC回写操作,写后清空flag
  4416. /// </summary>
  4417. /// <param name="modbusClient">modbus对象</param>
  4418. /// <param name="pLCReadDatas">读取到的数据字典</param>
  4419. /// <param name="pLCWriteDatas">需要写入的数据</param>
  4420. public static void PLCWriteData(ModbusClientHelper modbusClient, ref Dictionary<string, object> pLCReadDatas, ref Dictionary<string, WriteToPLC_Flag> pLCWriteDataDic)
  4421. {
  4422. if (pLCWriteDataDic != null && pLCWriteDataDic.Count > 0)
  4423. {
  4424. List<WriteToPLC_Flag> pLCWriteDatas = pLCWriteDataDic.Values.ToList();
  4425. for (int i = 0; i < pLCWriteDatas.Count; i++)
  4426. {
  4427. string mesFlagName = pLCWriteDatas[i].Name;
  4428. int mesFlagAdress = pLCWriteDatas[i].Adress;
  4429. short mesFlagValue = (short)pLCWriteDatas[i].Value; // short
  4430. if (mesFlagValue != 0) // 不为0则证明需要写入结果信息
  4431. {
  4432. // 先回写数据
  4433. List<WriteToPLC_Data> writeToPLCDatas = pLCWriteDatas[i].WriteToPLCDatas;
  4434. for (int j = 0; j < writeToPLCDatas.Count; j++)
  4435. {
  4436. int mesDataAdress = writeToPLCDatas[j].Adress;
  4437. PLCValueType mesDataType = writeToPLCDatas[j].ValueType;
  4438. switch (mesDataType)
  4439. {
  4440. case PLCValueType.Short:
  4441. short mesDataValueShort = (short)writeToPLCDatas[j].Value;
  4442. modbusClient.WriteMultipleRegisters<short>(mesDataAdress, mesDataValueShort);
  4443. break;
  4444. case PLCValueType.String:
  4445. string mesDataValueStr = (string)writeToPLCDatas[j].Value;
  4446. int mesDataValueStrLength = writeToPLCDatas[j].ValueTypeStrLength;
  4447. modbusClient.WriteMultipleRegisters<string>(mesDataAdress, mesDataValueStr, mesDataValueStrLength);
  4448. break;
  4449. }
  4450. }
  4451. // 再回写信号
  4452. modbusClient.WriteMultipleRegisters<short>(mesFlagAdress, mesFlagValue);
  4453. // 存储读取数据的字典
  4454. pLCReadDatas[mesFlagName] = (int)mesFlagValue;
  4455. // 存储写入数据的字典 - 清空写入值
  4456. pLCWriteDatas[i].Value = (short)0;
  4457. pLCWriteDataDic[mesFlagName] = pLCWriteDatas[i];
  4458. }
  4459. }
  4460. }
  4461. }
  4462. /// <summary>
  4463. /// 提交点检数据到MES - 取数据库中缓存的 点检数据
  4464. /// </summary>
  4465. /// <param name="no">3</param>
  4466. /// <param name="stationCode">设备编号</param>
  4467. /// <param name="stationNameStr">设备名称</param>
  4468. /// <param name="plcOrder">车间订单号</param>
  4469. private void SubmitOneCheckDataToMESByDB(int plcNo, int stationCode, string stationNameStr, string plcOrder)
  4470. {
  4471. try
  4472. {
  4473. /// [S2]FCT (2-上传点检数据;102-清空该工单该工单的所有点检项缓存)
  4474. /// [S3]值板机 (3-上传点检数据;103-清空该工单该工单的所有点检项缓存)
  4475. /// [S4]取放桁架 (4-上传点检数据;104-清空该工单该工单的所有点检项缓存)
  4476. /// [S6]CCD检测 (6-上传点检数据;106-清空该工单该工单的所有点检项缓存)
  4477. int result1 = 0;
  4478. switch (stationCode)
  4479. {
  4480. case 2:
  4481. case 3:
  4482. case 4:
  4483. case 6:
  4484. result1 = SubmitToMESByDB(stationCode.ToString(), stationNameStr, plcOrder);
  4485. break;
  4486. case 102:
  4487. result1 = ClearOneCheckDataByDB("2", stationNameStr, plcOrder);
  4488. break;
  4489. case 103:
  4490. result1 = ClearOneCheckDataByDB("3", stationNameStr, plcOrder);
  4491. break;
  4492. case 104:
  4493. result1 = ClearOneCheckDataByDB("4", stationNameStr, plcOrder);
  4494. break;
  4495. case 106:
  4496. result1 = ClearOneCheckDataByDB("6", stationNameStr, plcOrder);
  4497. break;
  4498. default:
  4499. // MES_Flag 为“6未找到正确设备编号”
  4500. //Funs[plcNo].WriteMultipleRegisters<int>(2406, 6);
  4501. AddMessage_Station(stationNameStr, LogType.Error, $"PLC通知上传点检数据到MES运行出错!未找到需要点检的正确设备编号");
  4502. return;
  4503. }
  4504. short result = result1 == 1 ? (short)1 : (short)2;
  4505. //Funs[plcNo].WriteMultipleRegisters<int>(2406, result); // MES_Flag 为4MES报错
  4506. WritePLCLog(LogType.Debug, $"PLC{plcNo}_PLC通知MES上传点检数据运行完毕!-Write" + (result == 1 ? "成功!" : "失败!"));
  4507. }
  4508. catch (Exception ex)
  4509. {
  4510. // MES_Flag 为2上位机报错
  4511. //Funs[plcNo].WriteMultipleRegisters<int>(2406, 2);
  4512. string str = ex.StackTrace;
  4513. AddMessage_Station(stationNameStr, LogType.Error, $"PLC通知上传点检数据到MES运行出错!错误信息:" + ex.Message.ToString() + ";异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  4514. }
  4515. }
  4516. #endregion 缓存读取到的PLC数据 与 需要写入的PLC数据
  4517. #region 日志
  4518. #region 各工位定制日志(同步至PLC交互页面)
  4519. /// <summary>
  4520. /// 添加日志
  4521. /// </summary>
  4522. /// <param name="stationNameStr">工站名称</param>
  4523. /// <param name="logType">日志类型</param>
  4524. /// <param name="message">日志内容</param>
  4525. /// <param name="snNumber">产品数字SN</param>
  4526. public void AddMessage_Station(string stationNameStr, LogType logType, string message, string snNumber = "")
  4527. {
  4528. if (!(stationNameStr.Equals("获取设备报警数据与状态信息")
  4529. && (message.Contains("更新整线运行数据完毕") || message.Contains("更新整线报警数据完毕"))
  4530. ))
  4531. {
  4532. AddMessage(logType, message); // 首页展示+日志记录
  4533. }
  4534. PLCDBFormMessage plcMessage = new PLCDBFormMessage()
  4535. {
  4536. StationName = stationNameStr,
  4537. SnNumber = snNumber,
  4538. Message = message,
  4539. CreateTime = DateTime.Now
  4540. };
  4541. // PLC交互页展示
  4542. Task.Run(() =>
  4543. {
  4544. try
  4545. {
  4546. if (Form_Main.formPLCDB != null && !Form_Main.formPLCDB.IsDisposed)
  4547. {
  4548. Form_Main.formPLCDB.UpdateMessage(plcMessage);
  4549. }
  4550. }
  4551. catch { }
  4552. });
  4553. }
  4554. #endregion 各工位定制日志(同步至PLC交互页面)
  4555. /// <summary>
  4556. /// 添加日志
  4557. /// </summary>
  4558. /// <param name="logType">日志类型</param>
  4559. /// <param name="message">日志内容</param>
  4560. public void AddMessage(LogType logType, string message)
  4561. {
  4562. OnMessage(logType, message);
  4563. string date = DateTime.Now.ToString("yyyy/MM/dd");
  4564. string time = DateTime.Now.ToString("HH:mm:ss:fff");
  4565. string msgShow = time + "--> " + message + "\r\n";
  4566. this.BeginInvoke(new Action(() =>
  4567. {
  4568. systemLog.Rows.Insert(0, date, time, message);
  4569. if (systemLog.Rows.Count >= 100)
  4570. systemLog.Rows.RemoveAt(systemLog.Rows.Count - 1);
  4571. }));
  4572. }
  4573. /// <summary>
  4574. /// 添加日志-保存
  4575. /// </summary>
  4576. /// <param name="logType">日志类型</param>
  4577. /// <param name="message">日志内容</param>
  4578. private void OnMessage(LogType logType, string msg)
  4579. {
  4580. MessageEvent?.Invoke(logType, msg);
  4581. }
  4582. /// <summary>
  4583. /// 保存PLC日志
  4584. /// </summary>
  4585. /// <param name="logType"></param>
  4586. /// <param name="logValue"></param>
  4587. private void WritePLCLog(LogType logType, string logValue)
  4588. {
  4589. switch ((int)logType)
  4590. {
  4591. case 0:
  4592. _PLCLogNet.WriteDebug(logValue);
  4593. break;
  4594. case 1:
  4595. _PLCLogNet.WriteInfo(logValue);
  4596. break;
  4597. case 2:
  4598. _PLCLogNet.WriteWarn(logValue);
  4599. break;
  4600. case 3:
  4601. _PLCLogNet.WriteError(logValue);
  4602. break;
  4603. default:
  4604. _PLCLogNet.WriteFatal(logValue);
  4605. break;
  4606. }
  4607. }
  4608. #endregion 日志
  4609. #region 保存数据
  4610. /// <summary>
  4611. /// 调用进站接口并保存进站数据
  4612. /// </summary>
  4613. /// <param name="stationNameStr">工站信息</param>
  4614. /// <param name="workorder_code">工单号</param>
  4615. /// <param name="mtltmrk">型号(物料号)</param>
  4616. /// <param name="sn">产品SN</param>
  4617. /// <param name="items">进站数据</param>
  4618. /// <returns>1成功;5MES报警;6上位机报警</returns>
  4619. public int SaveStationInData(string stationNameStr, string workorder_code, string mtltmrk, string sn, List<TestItem> items)
  4620. {
  4621. int result = 0;
  4622. XmMES_StationInRequest_Body inRequest_Body = new XmMES_StationInRequest_Body();
  4623. inRequest_Body.machineId = GlobalContext.S1_MachineId; // 装备ID(可配置)
  4624. inRequest_Body.stationId = GlobalContext.S1_StationId; // ⼯位ID(可配置)
  4625. inRequest_Body.clientMac = GlobalContext.MacStr; // 客⼾端本机MAC地址,格式:XX-XX-XX-XX-XX-XX
  4626. inRequest_Body.clientTime = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss.fff"); // 客⼾端请求时间,格式yyyy-MM-dd HH:mm:ss.fff
  4627. inRequest_Body.unitSn = sn; // 产品SN
  4628. inRequest_Body.userId = GlobalContext.MESUserId; // 用户ID;非必填
  4629. inRequest_Body.factoryId = GlobalContext.Factory_Code; // 工厂ID;非必填
  4630. string json_Body = JsonConvert.SerializeObject(inRequest_Body);
  4631. StationIn stationIn = new StationIn()
  4632. {
  4633. Workorder_code = workorder_code, // 车间订单号
  4634. Mtltmrk = mtltmrk, // 产品型号(物料号)
  4635. Sn = sn, // SN
  4636. StationIn_body = json_Body, // 进站接口Json数据 - Body
  4637. Parameter_values = items, // 进站数据
  4638. Write_user = inRequest_Body.userId, // 员工Id
  4639. Test_time = inRequest_Body.clientTime // 进站时间
  4640. };
  4641. // 本地数据
  4642. string sql = stationIn.ToStringInsert(0);
  4643. string ret = SQLHelper_New.ExecuteNonQuery(sql, null);
  4644. result = ret == "成功" ? 1 : 6;
  4645. AddMessage_Station(stationNameStr, LogType.Info, string.Concat(stationNameStr, "_保存本地进站数据---" + ret));
  4646. //await Task.Delay(200);
  4647. // 上传MES
  4648. if (GlobalContext.IsSendStationIn)
  4649. {
  4650. try
  4651. {
  4652. XmMES_StationInResponse response = new XmMES_StationInResponse();
  4653. string mesRet = string.Empty;
  4654. int i = 0;
  4655. while (i < 2) // 1009会多次尝试上传
  4656. {
  4657. response = XiaomiMESHttp_StationInbound.StationIn(inRequest_Body);
  4658. if (response != null && response.header.code == "200")
  4659. break;
  4660. else if (!mesRet.Contains("1009")) // 1009是未知错误
  4661. i++;
  4662. i++;
  4663. mesRet = $"[{response?.header?.code}]{response?.header?.desc}";
  4664. // 记录失败原因
  4665. OnMessage(LogType.Error, "上传出站数据到MES服务器---失败!正在重新上传!接口报错信息:" + mesRet + "参数:" + json_Body);
  4666. }
  4667. AddMessage_Station(stationNameStr, LogType.Info, stationNameStr + "_上传进站数据到MES服务器---" + mesRet);
  4668. if (response?.header?.code == "200")
  4669. {
  4670. string sql_Upd = stationIn.ToStringUpdateStatusByID(1);
  4671. string ret_Upd = SQLHelper_New.ExecuteNonQuery(sql_Upd, null);
  4672. result = ret_Upd == "成功" ? 1 : 6;
  4673. AddMessage_Station(stationNameStr, LogType.Info, $"更新【进站数据 id {stationIn.GUID}】上传状态---" + ret_Upd);
  4674. }
  4675. else
  4676. {
  4677. result = 5;
  4678. OnMessage(LogType.Error, "上传进站数据到MES服务器---失败!接口报错信息:" + mesRet + "参数:" + json_Body);
  4679. }
  4680. }
  4681. catch (Exception ex)
  4682. {
  4683. result = 6;
  4684. string str = ex.StackTrace;
  4685. AddMessage_Station(stationNameStr, LogType.Error, $"PLC上传进站数据MES报错!错误信息:" + ex.Message.ToString() + ";异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  4686. }
  4687. }
  4688. return result;
  4689. }
  4690. /// <summary>
  4691. /// 选择如何记录出站数据
  4692. /// </summary>
  4693. /// <param name="items">出站数据</param>
  4694. /// <param name="equipmentCode">设备编号</param>
  4695. /// <param name="processItem">测试项目</param>
  4696. /// <param name="workorder_code">车间订单号</param>
  4697. /// <param name="batch_num">批次号</param>
  4698. /// <param name="mtltmrk">型号</param>
  4699. /// <param name="proDate">日期</param>
  4700. /// <param name="supplierCode">供应商代码</param>
  4701. /// <param name="sn_Number">产品序列号的 数字序列部分</param>
  4702. /// <returns>上传成功时返回1;失败返回0</returns>
  4703. private int SwitctProcessData(string stationNameStr, List<TestItem> items, string equipmentCode, string processItem,
  4704. string workorder_code, string batch_num, string mtltmrk, string proDate,
  4705. string supplierCode, string sn, bool pass, string vehicleSn, string vehicleSlot)
  4706. {
  4707. return SaveProcessDataByDB(stationNameStr, items, equipmentCode, processItem, workorder_code, batch_num, mtltmrk,
  4708. proDate, supplierCode, sn, pass, vehicleSn, vehicleSlot);
  4709. }
  4710. /// <summary>
  4711. /// 添加出站数据(提交到MES+本地保存到数据库)
  4712. /// </summary>
  4713. /// <param name="items">出站数据</param>
  4714. /// <param name="equipmentCode">设备编号</param>
  4715. /// <param name="processItem">测试项目</param>
  4716. /// <param name="workorder_code">车间订单号</param>
  4717. /// <param name="batch_num">批次号</param>
  4718. /// <param name="mtltmrk">型号</param>
  4719. /// <param name="proDate">日期</param>
  4720. /// <param name="supplierCode">供应商代码</param>
  4721. /// <param name="sn_Number">产品序列号的 数字序列部分</param>
  4722. /// <returns>上传成功时返回1;失败返回0</returns>
  4723. public int SaveProcessDataByDB(string stationNameStr, List<TestItem> items, string equipmentCode,
  4724. string processItem, string workorder_code, string batch_num, string mtltmrk,
  4725. string proDate, string supplierCode, string sn, bool pass, string vehicleSn, string vehicleSlot)
  4726. {
  4727. int upload = 0;
  4728. int result = 0;
  4729. ProcessData processData = new ProcessData()
  4730. {
  4731. Equipment_code = equipmentCode,
  4732. Workorder_code = workorder_code,
  4733. Batch_number = batch_num,
  4734. Sn = sn, // SN
  4735. Testitem = processItem,
  4736. Parameter_values = items,
  4737. Write_user = GlobalContext.CurrentUser,
  4738. Test_time = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss.fff")
  4739. };
  4740. // 本地数据
  4741. string sql = processData.ToStringInsert(upload);
  4742. string ret = SQLHelper_New.ExecuteNonQuery(sql, null);
  4743. AddMessage_Station(stationNameStr, LogType.Info, string.Concat("[[", equipmentCode, "]", stationNameStr, "]保存本地出站数据---" + ret));
  4744. // 上传MES
  4745. if (GlobalContext.IsSendProcessData)
  4746. {
  4747. try
  4748. {
  4749. string id = processData.ID.Copy();
  4750. XmMES_StationOutRequest_Body outRequest_Body = new XmMES_StationOutRequest_Body();
  4751. outRequest_Body.machineId = GlobalContext.S1_MachineId; // 装备id(可配置) // ZS
  4752. outRequest_Body.stationId = GlobalContext.S1_StationId; // ⼯位ID(可配置) // ZS
  4753. outRequest_Body.clientMac = GlobalContext.MacStr; // 客⼾端本机MAC地址,格式:XX-XX-XX-XX-XX-XX
  4754. outRequest_Body.clientTime = processData.Test_time; // 客⼾端请求时间,格式yyyy-MM-dd HH:mm:ss.fff
  4755. outRequest_Body.unitSn = sn; // 产品SN
  4756. outRequest_Body.state = pass ? "PASS" : "FAIL"; // 出站条件 PASS或FAIL
  4757. outRequest_Body.userId = GlobalContext.MESUserId; // ⽤⼾ID;非必填
  4758. outRequest_Body.factoryId = GlobalContext.Factory_Code; // ⼯⼚id;非必填
  4759. outRequest_Body.unitData.vehicleData.Add(
  4760. new XmMES_StationOutRequest_Body.XmStationOut_VehicleData()
  4761. {
  4762. vehicleSn = vehicleSn,
  4763. vehicleType = string.Empty,
  4764. slot = vehicleSlot
  4765. }); // 设备数据 - 载具信息
  4766. string jsonstr1 = JsonConvert.SerializeObject(outRequest_Body);
  4767. if (GlobalContext.IsSendProcessData)
  4768. {
  4769. XmMES_StationOutResponse response = new XmMES_StationOutResponse();
  4770. string mesRet = string.Empty;
  4771. int i = 0;
  4772. while (i < 2) // 1009会多次尝试上传
  4773. {
  4774. response = XiaomiMESHttp_StationOutbound.StationOut(outRequest_Body);
  4775. if (response != null && response.header.code == "200")
  4776. break;
  4777. else if (!mesRet.Contains("1009")) // 1009是未知错误
  4778. i++;
  4779. i++;
  4780. mesRet = $"[{response?.header?.code}]{response?.header?.desc}";
  4781. // 记录失败原因
  4782. OnMessage(LogType.Error, "上传出站数据到MES服务器---失败!正在重新上传!接口报错信息:" + mesRet + "参数:" + jsonstr1);
  4783. }
  4784. AddMessage_Station(stationNameStr, LogType.Info, "[" + processItem + "]上传出站数据到MES服务器---" + mesRet);
  4785. if (response?.header?.code == "200")
  4786. {
  4787. string sql_Upd = ProcessData.ToStringUpdateStatusByID(1, id);
  4788. string ret_Upd = SQLHelper_New.ExecuteNonQuery(sql_Upd, null);
  4789. result = 1;
  4790. AddMessage_Station(stationNameStr, LogType.Info, $"更新【出站数据 id {id}】上传状态---" + ret_Upd);
  4791. }
  4792. else
  4793. {
  4794. OnMessage(LogType.Error, "上传出站数据到MES服务器---失败!接口报错信息:" + mesRet + "参数:" + jsonstr1);
  4795. }
  4796. }
  4797. }
  4798. catch (Exception ex)
  4799. {
  4800. string str = ex.StackTrace;
  4801. AddMessage_Station(stationNameStr, LogType.Error, $"PLC上传出站数据MES报错!错误信息:" + ex.Message.ToString() + ";异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  4802. }
  4803. }
  4804. return result;
  4805. }
  4806. /// <summary>
  4807. /// 选择如何记录点检数据
  4808. /// </summary>
  4809. /// <param name="names"></param>
  4810. /// <param name="contents"></param>
  4811. /// <param name="results"></param>
  4812. /// <param name="equipmentCode"></param>
  4813. /// <param name="stationNameStr"></param>
  4814. private int SwitctOneCheckData(OneCheckData oneCheckData, string equipmentCode, string stationNameStr)
  4815. {
  4816. //if (DataSwitch == 1)
  4817. //{
  4818. return SaveOneCheckDataByDB(oneCheckData, equipmentCode, stationNameStr);
  4819. //}
  4820. //else // 废弃
  4821. //{
  4822. // SaveOneCheckData(names, contents, results, equipmentCode, stationNameStr);
  4823. //}
  4824. }
  4825. /// <summary>
  4826. /// 添加点检数据ByDB(本地保存;不提交到MES)
  4827. /// </summary>
  4828. /// <param name="oneCheckData">点检数据</param>
  4829. /// <param name="equipmentCode">设备编号</param>
  4830. /// <param name="stationNameStr">工站名称</param>
  4831. public int SaveOneCheckDataByDB(OneCheckData oneCheckData, string equipmentCode, string stationNameStr)
  4832. {
  4833. int upload = 0;
  4834. //本地数据保存
  4835. string sql = oneCheckData.ToStringInsert(upload);
  4836. string ret = SQLHelper_New.ExecuteNonQuery(sql, null);
  4837. AddMessage_Station(stationNameStr, LogType.Info, string.Concat("[[", equipmentCode, "]", stationNameStr, "]保存本地点检数据---", ret));
  4838. //Task.Run(() => // 上传mes-异步
  4839. //{
  4840. // //上传mes
  4841. // string jsonstr = JsonConvert.SerializeObject(oneCheckData);
  4842. // if (GlobalContext.IsSendCheckOneData)
  4843. // {
  4844. // string url = @"HTTP://" + GlobalContext.ServerHost + ":" + GlobalContext.ServerPort + @"/api/ProductionLine/OneCheckData";
  4845. // string mesRet = HttpUitls.SubmitDataToMES(url, jsonstr);
  4846. // AddMessage_Station(stationNameStr, LogType.Info, string.Concat("[[", equipmentCode, "]", stationNameStr, "]上传点检数据到MES---", mesRet));
  4847. // if (mesRet == "成功")
  4848. // {
  4849. // // 更新上传状态
  4850. // string sql_Upd = OneCheckData.ToStringUpdateStatusByID(1, oneCheckData.ID);
  4851. // string ret_Upd = SQLHelper_New.ExecuteNonQuery(sql_Upd, null);
  4852. // AddMessage_Station(stationNameStr, LogType.Info, $"更新【点检数据 id {oneCheckData.ID}】上传状态---" + ret_Upd);
  4853. // }
  4854. // }
  4855. //});
  4856. return ret == "成功" ? 1 : 0;
  4857. }
  4858. /// <summary>
  4859. /// 提交点检数据到MES
  4860. /// </summary>
  4861. /// <param name="procedure_code">工序编号 = 设备编号</param>
  4862. /// <param name="plcOrder">车间订单号</param>
  4863. /// <returns></returns>
  4864. public int SubmitToMESByDB(string procedure_code, string stationNameStr, string plcOrder)
  4865. {
  4866. // 获取今天的点检数据
  4867. string querySQL_Today = new OneCheckData().ToQuerySQL_Today(procedure_code, plcOrder);
  4868. DataSet ds = SQLHelper_New.Query(querySQL_Today, null);
  4869. if (ds != null && ds.Tables.Count > 0 && ds.Tables[0].Rows.Count > 0)
  4870. {
  4871. // 拼接所有点检数据
  4872. OneCheckData oneCheckDatas_MES = new OneCheckData()
  4873. {
  4874. ID = ds.Tables[0].Rows[0][0].ToString(),
  4875. Line_code = ds.Tables[0].Rows[0][1].ToString(),
  4876. Line_name = ds.Tables[0].Rows[0][2].ToString(),
  4877. Equipment_code = ds.Tables[0].Rows[0][3].ToString(),
  4878. Equipment_name = ds.Tables[0].Rows[0][4].ToString(),
  4879. Workorder_code = ds.Tables[0].Rows[0][5].ToString(),
  4880. Procedure_code = ds.Tables[0].Rows[0][6].ToString(),
  4881. Procedure_name = ds.Tables[0].Rows[0][7].ToString(),
  4882. Onecheck_empcode = ds.Tables[0].Rows[0][8].ToString(),
  4883. Onecheck_empname = ds.Tables[0].Rows[0][9].ToString(),
  4884. Onecheck_time = ds.Tables[0].Rows[0][10].ToString()
  4885. };
  4886. List<string> upd_Ids = new List<string>();
  4887. foreach (DataRow row in ds.Tables[0].Rows)
  4888. {
  4889. var obj1 = row["Oneckeck_values"];
  4890. if (obj1 != null)
  4891. {
  4892. upd_Ids.Add(row["ID"].ToString());
  4893. List<OneCheckItem> item = JsonConvert.DeserializeObject<List<OneCheckItem>>(obj1.ToString());
  4894. oneCheckDatas_MES.Oneckeck_values.AddRange(item);
  4895. }
  4896. }
  4897. //上传mes
  4898. string jsonstr = JsonConvert.SerializeObject(oneCheckDatas_MES);
  4899. if (GlobalContext.IsSendCheckOneData)
  4900. {
  4901. string url = @"HTTP://" + GlobalContext.ServerHost + ":" + @"/api/ProductionLine/OneCheckData";
  4902. string mesRet = HttpUitls.SubmitDataToMES(url, jsonstr);
  4903. AddMessage_Station(stationNameStr, LogType.Info, string.Concat("[", stationNameStr, "]PLC通知上传点检数据到MES到---", mesRet));
  4904. if (mesRet == "成功")
  4905. {
  4906. // 更新上传状态
  4907. string sql_Upd = OneCheckData.ToStringUpdateStatusByIDs(1, upd_Ids);
  4908. string ret_Upd = SQLHelper_New.ExecuteNonQuery(sql_Upd, null);
  4909. AddMessage_Station(stationNameStr, LogType.Info, $"更新【点检数据 id [{string.Join("','", upd_Ids)}]】上传状态---" + ret_Upd);
  4910. // 保存最新一条点检数据 到文件中
  4911. StandardLibrary.IniFile.INIWriteValue(GlobalContext.CheckOneDataPath, "S" + procedure_code, "WorkOrderCode", GlobalContext.WorkOrderCode);
  4912. StandardLibrary.IniFile.INIWriteValue(GlobalContext.CheckOneDataPath, "S" + procedure_code, "Oneckeck_values", JsonConvert.SerializeObject(oneCheckDatas_MES.Oneckeck_values));
  4913. return ret_Upd == "成功" ? 1 : 0;
  4914. }
  4915. }
  4916. }
  4917. //else
  4918. //{
  4919. // AddMessage_Station(stationNameStr, LogType.Info, string.Concat("[", stationNameStr, "]PLC通知上传点检数据到MES---失败!今天还未点检。"));
  4920. //}
  4921. return 0;
  4922. }
  4923. /// <summary>
  4924. /// 添加点检数据ByDB(本地保存 + 提交到MES)
  4925. /// </summary>
  4926. /// <param name="oneCheckData">点检数据</param>
  4927. /// <param name="equipmentCode">设备编号</param>
  4928. /// <param name="stationNameStr">工站名称</param>
  4929. /// <returns></returns>
  4930. public int SaveOneCheckDataByDBAndSubmit(OneCheckData oneCheckData, string equipmentCode, string stationNameStr)
  4931. {
  4932. int upload = 0;
  4933. //本地数据保存
  4934. string sql = oneCheckData.ToStringInsert(upload);
  4935. string ret = SQLHelper_New.ExecuteNonQuery(sql, null);
  4936. AddMessage_Station(stationNameStr, LogType.Info, string.Concat("[[", equipmentCode, "]", stationNameStr, "]保存本地点检数据---", ret));
  4937. Task.Run(() => // 上传mes-异步
  4938. {
  4939. //上传mes
  4940. string jsonstr = JsonConvert.SerializeObject(oneCheckData);
  4941. string jsonItems = JsonConvert.SerializeObject(oneCheckData.Oneckeck_values);
  4942. if (GlobalContext.IsSendCheckOneData)
  4943. {
  4944. string url = @"HTTP://" + GlobalContext.ServerHost + ":" + @"/api/ProductionLine/OneCheckData";
  4945. string mesRet = HttpUitls.SubmitDataToMES(url, jsonstr);
  4946. AddMessage_Station(stationNameStr, LogType.Info, string.Concat("[[", equipmentCode, "]", stationNameStr, "]上传点检数据到MES---", mesRet));
  4947. if (mesRet == "成功")
  4948. {
  4949. // 更新上传状态
  4950. string sql_Upd = OneCheckData.ToStringUpdateStatusByID(1, oneCheckData.ID);
  4951. string ret_Upd = SQLHelper_New.ExecuteNonQuery(sql_Upd, null);
  4952. AddMessage_Station(stationNameStr, LogType.Info, $"更新【点检数据 id {oneCheckData.ID}】上传状态---" + ret_Upd);
  4953. // 保存最新一条点检数据 到文件中
  4954. StandardLibrary.IniFile.INIWriteValue(GlobalContext.CheckOneDataPath, equipmentCode, "WorkOrderCode", GlobalContext.WorkOrderCode);
  4955. StandardLibrary.IniFile.INIWriteValue(GlobalContext.CheckOneDataPath, equipmentCode, "Oneckeck_values", jsonItems);
  4956. }
  4957. }
  4958. });
  4959. return ret == "成功" ? 1 : 0;
  4960. }
  4961. /// <summary>
  4962. /// 清空 点检数据 By 工序号、订单号
  4963. /// </summary>
  4964. /// <param name="procedure_code">工序号</param>
  4965. /// <param name="stationNameStr">工站号</param>
  4966. /// <param name="plcOrder">订单号</param>
  4967. /// <returns></returns>
  4968. /// <exception cref="NotImplementedException"></exception>
  4969. private int ClearOneCheckDataByDB(string procedure_code, string stationNameStr, string plcOrder)
  4970. {
  4971. // 清空
  4972. string sql_Det = OneCheckData.ToDeteleByProcedurecodeAndPlcOrder(procedure_code, plcOrder);
  4973. string ret_Upd = SQLHelper_New.ExecuteNonQuery(sql_Det, null);
  4974. AddMessage_Station(stationNameStr, LogType.Info, $"清空【工位编号{procedure_code}】【车间订单{plcOrder}】的点检项缓存 ---" + ret_Upd);
  4975. return ret_Upd == "成功" ? 1 : 2;
  4976. }
  4977. /// <summary>
  4978. /// 生产过程中,自动判断 是否 使用上次的点检数据
  4979. /// 在工单加工第一个产品时触发该方法
  4980. /// 如果工单是上次的点检工单则直接返回成功,工单不是上次的点检工单则使用上个工单的点检数据,上传点检信息
  4981. /// </summary>
  4982. /// <param name="stationNameStr"></param>
  4983. /// <param name="equipmentCode">设备编号</param>
  4984. /// <param name="accno">工序编号</param>
  4985. /// <param name="processItem">点检数据</param>
  4986. /// <returns></returns>
  4987. private int SwitctOneCheckData_First(string stationNameStr, string equipmentCode, string accno, string processItem)
  4988. {
  4989. string WorkOrderCode = StandardLibrary.IniFile.INIGetStringValue(GlobalContext.CheckOneDataPath, equipmentCode, "WorkOrderCode", string.Empty);
  4990. //如果当前工单和记录中的工单是一致,表示这个工单是需要点检的,跳过
  4991. //如果当前工单和记录中的工单是不一致,表示这个工单和上个工单是同型号的,可以使用上个工单的点检数据
  4992. if (GlobalContext.WorkOrderCode == WorkOrderCode)
  4993. {
  4994. return 1;
  4995. }
  4996. //点检数据
  4997. string Oneckeck_values = StandardLibrary.IniFile.INIGetStringValue(GlobalContext.CheckOneDataPath, equipmentCode, "Oneckeck_values", string.Empty);
  4998. List<OneCheckItem> items = new List<OneCheckItem>();
  4999. try
  5000. {
  5001. items = JsonConvert.DeserializeObject<List<OneCheckItem>>(Oneckeck_values);
  5002. }
  5003. catch (Exception ex)
  5004. {
  5005. return 0;
  5006. }
  5007. // 拼接所有点检数据
  5008. OneCheckData oneCheckDatas_MES = new OneCheckData()
  5009. {
  5010. ID = Guid.NewGuid().ToString(),
  5011. Line_code = GlobalContext.LineCode,
  5012. Line_name = GlobalContext.LineName,
  5013. Equipment_code = equipmentCode,
  5014. Equipment_name = equipmentCode,
  5015. Workorder_code = GlobalContext.WorkOrderCode,
  5016. Procedure_code = accno,
  5017. Procedure_name = processItem,
  5018. Onecheck_empcode = "",
  5019. Onecheck_empname = "",
  5020. Onecheck_time = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss.fff"),
  5021. Oneckeck_values = items
  5022. };
  5023. // 本地保存 + 提交到MES
  5024. return SaveOneCheckDataByDBAndSubmit(oneCheckDatas_MES, equipmentCode, stationNameStr);
  5025. }
  5026. /// <summary>
  5027. /// 添加报警数据ByDB(提交到MES+本地保存)
  5028. /// </summary>
  5029. /// <param name="alarmData">数据</param>
  5030. /// <param name="isUpd">更新而不是新增</param>
  5031. public void SaveAlarmDataByDB(string stationNameStr, AlarmData alarmData, bool isUpd)
  5032. {
  5033. if (isUpd)
  5034. {
  5035. string sql = alarmData.ToStringUpdate();
  5036. SQLHelper_New.ExecuteSQL(sql, null);
  5037. AddMessage_Station(stationNameStr, LogType.Info, "消除报警[" + alarmData.LineName + "-" + alarmData.AlarmDesc + "]完毕!");
  5038. }
  5039. else
  5040. {
  5041. string sql = alarmData.ToStringInsert();
  5042. SQLHelper_New.ExecuteSQL(sql, null);
  5043. AddMessage_Station(stationNameStr, LogType.Info, "发生了报警[" + alarmData.LineName + "-" + alarmData.AlarmDesc + "]!");
  5044. }
  5045. }
  5046. /// <summary>
  5047. /// 上传节拍数据
  5048. /// </summary>
  5049. /// <returns></returns>
  5050. public (short, string) SaveOEEData(int plcNo, string stationNameStr, XiaomiDeviceOEE deviceOEE, string oEEPartNo, string oEEProductSN)
  5051. {
  5052. // 上传OEE
  5053. if (GlobalContext.IsMqttStationInputBegin)
  5054. {
  5055. Task.Run(() =>
  5056. {
  5057. try
  5058. {
  5059. StationInputBeginRequest oee = new StationInputBeginRequest();
  5060. oee.action = deviceOEE.ToString(); // 节拍动作(XiaomiDeviceOEE)
  5061. oee.beat_tm = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss.fff"); // 节拍发⽣时间
  5062. oee.action_subject = oEEPartNo; // 该动作操作的⽬标对象(SN)
  5063. oee.action_subject_parent = oEEProductSN; // ⼤板SN/载具SN
  5064. oee.action_location = "ZS"; // ZS 该动作的位置信息(⼯位、槽位),如:F06-GSTPLA11_01-SLOT-01
  5065. oee.action_material = string.Empty; // 该动作的物料信息
  5066. oee.extra = string.Empty; // 额外信息
  5067. oee.class_level_1 = string.Empty; // 分类层级1
  5068. oee.class_level_2 = string.Empty; // 分类层级2
  5069. oee.class_level_3 = string.Empty; // 分类层级3
  5070. int result = XiaomiMqttClient_Extend.Write_StationInputBegin(oee);
  5071. string msg = $"[{result}]";
  5072. bool errCodeParse = Enum.TryParse(result.ToString(), out XiaomiMqttResponse_ErrCode errCode);
  5073. msg += errCodeParse ? errCode.ToString() : "ERR_UNKOWN";
  5074. AddMessage(LogType.Info, stationNameStr + $"_异步上传节拍接口;接口结果:-- {msg}");
  5075. }
  5076. catch (Exception ex)
  5077. {
  5078. string str = ex.StackTrace;
  5079. AddMessage(LogType.Error, $"PLC{plcNo}_{stationNameStr} 异步上传节拍接口出错!错误信息:" + ex.Message + "异常位置:" + str.Substring(str.LastIndexOf("\\") + 1, str.Length - str.LastIndexOf("\\") - 1));
  5080. }
  5081. });
  5082. return ((short)1, "异步上传中!");
  5083. }
  5084. else
  5085. return ((short)1, "未启用上传!");
  5086. }
  5087. /// <summary>
  5088. /// 回调方法- With DataId
  5089. /// </summary>
  5090. /// <param name="id"></param>
  5091. /// <param name="v"></param>
  5092. /// <param name="dataId"></param>
  5093. public void CallbackWithDataId(string id, string msg, string dataId)
  5094. {
  5095. //_MqttLogNet.WriteInfo("-------CallbackWithDataId-------");
  5096. //byte[] buffer1 = Encoding.Default.GetBytes(v);
  5097. //byte[] buffer2 = Encoding.Convert(Encoding.UTF8, Encoding.Default, buffer1, 0, buffer1.Length);
  5098. //string strBuffer = Encoding.Default.GetString(buffer2, 0, buffer2.Length);
  5099. //Console.WriteLine("{0} -> {1} {2}", id, strBuffer, dataId);
  5100. string datetime = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss.fff");
  5101. _MqttLogNet.WriteInfo($"{datetime}-> [消息ID:{id}][事件ID:{dataId}]{msg}");
  5102. }
  5103. #endregion 保存数据
  5104. #region UI刷新
  5105. /// <summary>
  5106. /// 更新商品信息的UI + 下发产品信息(SN)
  5107. /// </summary>
  5108. private void UpdateProductInfo()
  5109. {
  5110. currentBN.Text = GlobalContext.BatchNumber; // 批次号
  5111. currentWC.Text = GlobalContext.WorkOrderCode; // 订单号
  5112. currentMtltmrk.Text = GlobalContext.Mtltmrk; // 产品型号
  5113. txt_CurSupplierCode.Text = ""; // 供应商代号
  5114. // 下传给1号机,判断下plc对象数量
  5115. //if (Funs.Count > 1)
  5116. //{
  5117. // DownLoadProductInfo(1);
  5118. //}
  5119. }
  5120. /// <summary>
  5121. /// 更新PLC连接状态的UI
  5122. /// </summary>
  5123. /// <param name="no">PLC编号</param>
  5124. /// <param name="status">状态</param>
  5125. private void UpdatePLCMonitor(int imgNo, int plcNo, int status)
  5126. {
  5127. if (this != null && !this.IsDisposed)
  5128. {
  5129. switch (imgNo)
  5130. {
  5131. case 1:
  5132. this.BeginInvoke(new Action(() =>
  5133. {
  5134. pictureBox1.Image = imageListState.Images[status];
  5135. }));
  5136. break;
  5137. case 2:
  5138. this.BeginInvoke(new Action(() =>
  5139. {
  5140. pictureBox2.Image = imageListState.Images[status];
  5141. }));
  5142. break;
  5143. case 3:
  5144. this.BeginInvoke(new Action(() =>
  5145. {
  5146. pictureBox3.Image = imageListState.Images[status];
  5147. }));
  5148. break;
  5149. case 4:
  5150. this.BeginInvoke(new Action(() =>
  5151. {
  5152. pictureBox4.Image = imageListState.Images[status];
  5153. }));
  5154. break;
  5155. case 5:
  5156. this.BeginInvoke(new Action(() =>
  5157. {
  5158. pictureBox5.Image = imageListState.Images[status];
  5159. }));
  5160. break;
  5161. case 6:
  5162. this.BeginInvoke(new Action(() =>
  5163. {
  5164. pictureBox6.Image = imageListState.Images[status];
  5165. }));
  5166. break;
  5167. case 7:
  5168. this.BeginInvoke(new Action(() =>
  5169. {
  5170. pictureBox7.Image = imageListState.Images[status];
  5171. }));
  5172. break;
  5173. case 8:
  5174. this.BeginInvoke(new Action(() =>
  5175. {
  5176. pictureBox8.Image = imageListState.Images[status];
  5177. }));
  5178. break;
  5179. case 9:
  5180. this.BeginInvoke(new Action(() =>
  5181. {
  5182. pictureBox9.Image = imageListState.Images[status];
  5183. }));
  5184. break;
  5185. default:
  5186. break;
  5187. }
  5188. }
  5189. Task.Run(() => // 更新PLC交互页的指示灯
  5190. {
  5191. try
  5192. {
  5193. if (Form_Main.formPLCDB != null && !Form_Main.formPLCDB.IsDisposed)
  5194. {
  5195. Form_Main.formPLCDB.UpdatePLCFunMonitor(plcNo, status);
  5196. }
  5197. }
  5198. catch { }
  5199. });
  5200. }
  5201. #endregion UI刷新
  5202. /// <summary>
  5203. /// 实例化报警字典
  5204. /// </summary>
  5205. private void InitalDicAlarm()
  5206. {
  5207. #region 第一个工站(这里未区分工位,所以下面出现的‘工位代码’使用‘线别代码’代替)
  5208. List<Alarm> keyValues1 = new List<Alarm>
  5209. {
  5210. #region 第一组报警(电机)
  5211. new Alarm { 报警类型 = "电机故障", 报警详情 = "料盘搬运_Y轴电机故障" ,关联的PLC地址 = 5100 },
  5212. new Alarm { 报警类型 = "电机故障", 报警详情 = "壳体取料_X轴电机故障" ,关联的PLC地址 = 5101 },
  5213. new Alarm { 报警类型 = "电机故障", 报警详情 = "壳体取料_Z轴电机故障" ,关联的PLC地址 = 5102 },
  5214. new Alarm { 报警类型 = "电机故障", 报警详情 = "载具搬运_X轴电机故障" ,关联的PLC地址 = 5103 },
  5215. new Alarm { 报警类型 = "电机故障", 报警详情 = "镭射_X轴电机故障" ,关联的PLC地址 = 5104 },
  5216. new Alarm { 报警类型 = "电机故障", 报警详情 = "上相机_X轴电机故障" ,关联的PLC地址 = 5105 },
  5217. new Alarm { 报警类型 = "电机故障", 报警详情 = "上相机_Z轴电机故障" ,关联的PLC地址 = 5106 },
  5218. new Alarm { 报警类型 = "电机故障", 报警详情 = "下相机_X轴电机故障" ,关联的PLC地址 = 5107 },
  5219. new Alarm { 报警类型 = "电机故障", 报警详情 = "下料_Y轴电机故障" ,关联的PLC地址 = 5108 },
  5220. new Alarm { 报警类型 = "电机故障", 报警详情 = "下料_X轴电机故障" ,关联的PLC地址 = 5109 },
  5221. #endregion 第一组报警(电机)
  5222. #region 第二组报警(气缸)
  5223. new Alarm { 报警类型 = "气缸故障", 报警详情 = "上料仓分料进退气缸故障" ,关联的PLC地址 = 5200 },
  5224. new Alarm { 报警类型 = "气缸故障", 报警详情 = "上料仓分料升降气缸故障" ,关联的PLC地址 = 5201 },
  5225. new Alarm { 报警类型 = "气缸故障", 报警详情 = "上料仓顶升气缸故障" ,关联的PLC地址 = 5202 },
  5226. new Alarm { 报警类型 = "气缸故障", 报警详情 = "壳体取料夹爪气缸故障" ,关联的PLC地址 = 5203 },
  5227. new Alarm { 报警类型 = "气缸故障", 报警详情 = "下料仓顶升气缸故障" ,关联的PLC地址 = 5204 },
  5228. new Alarm { 报警类型 = "气缸故障", 报警详情 = "壳体上料平移气缸故障" ,关联的PLC地址 = 5205 },
  5229. new Alarm { 报警类型 = "气缸故障", 报警详情 = "壳体上料升降气缸故障" ,关联的PLC地址 = 5206 },
  5230. new Alarm { 报警类型 = "气缸故障", 报警详情 = "壳体上料夹爪气缸故障" ,关联的PLC地址 = 5207 },
  5231. new Alarm { 报警类型 = "气缸故障", 报警详情 = "壳体上料旋转气缸故障" ,关联的PLC地址 = 5208 },
  5232. new Alarm { 报警类型 = "气缸故障", 报警详情 = "胶圈组装平移气缸故障" ,关联的PLC地址 = 5209 },
  5233. new Alarm { 报警类型 = "气缸故障", 报警详情 = "胶圈组装升降气缸故障" ,关联的PLC地址 = 5210 },
  5234. new Alarm { 报警类型 = "气缸故障", 报警详情 = "胶圈组装夹爪气缸故障" ,关联的PLC地址 = 5211 },
  5235. new Alarm { 报警类型 = "气缸故障", 报警详情 = "胶圈组装撑开气缸故障" ,关联的PLC地址 = 5212 },
  5236. new Alarm { 报警类型 = "气缸故障", 报警详情 = "载具定位气缸1故障" ,关联的PLC地址 = 5213 },
  5237. new Alarm { 报警类型 = "气缸故障", 报警详情 = "载具定位气缸2故障" ,关联的PLC地址 = 5214 },
  5238. new Alarm { 报警类型 = "气缸故障", 报警详情 = "载具下料移载气缸故障" ,关联的PLC地址 = 5215 },
  5239. new Alarm { 报警类型 = "气缸故障", 报警详情 = "载具侧推气缸故障" ,关联的PLC地址 = 5216 },
  5240. new Alarm { 报警类型 = "气缸故障", 报警详情 = "载具回流气缸故障" ,关联的PLC地址 = 5217 },
  5241. new Alarm { 报警类型 = "气缸故障", 报警详情 = "工位2压料气缸故障" ,关联的PLC地址 = 5218 },
  5242. new Alarm { 报警类型 = "气缸故障", 报警详情 = "工位2电测气缸故障" ,关联的PLC地址 = 5219 },
  5243. new Alarm { 报警类型 = "气缸故障", 报警详情 = "工位2气密气缸故障" ,关联的PLC地址 = 5220 },
  5244. new Alarm { 报警类型 = "气缸故障", 报警详情 = "工位3下压气缸故障" ,关联的PLC地址 = 5221 },
  5245. new Alarm { 报警类型 = "气缸故障", 报警详情 = "工位3上顶气缸故障" ,关联的PLC地址 = 5222 },
  5246. new Alarm { 报警类型 = "气缸故障", 报警详情 = "工位5相机升降气缸故障" ,关联的PLC地址 = 5223 },
  5247. new Alarm { 报警类型 = "气缸故障", 报警详情 = "下料模组升降气缸故障" ,关联的PLC地址 = 5224 },
  5248. new Alarm { 报警类型 = "气缸故障", 报警详情 = "下料模组夹爪气缸1故障" ,关联的PLC地址 = 5225 },
  5249. new Alarm { 报警类型 = "气缸故障", 报警详情 = "下料模组夹爪气缸2故障" ,关联的PLC地址 = 5226 },
  5250. new Alarm { 报警类型 = "气缸故障", 报警详情 = "机械手夹爪气缸故障" ,关联的PLC地址 = 5227 },
  5251. new Alarm { 报警类型 = "气缸故障", 报警详情 = "工位4:镭射压料气缸故障" ,关联的PLC地址 = 5228 },
  5252. #endregion 第二组报警(气缸)
  5253. #region 第三组报警(其他故障)
  5254. new Alarm { 报警类型 = "其他故障", 报警详情 = "上料处缺料报警" ,关联的PLC地址 = 5300 },
  5255. new Alarm { 报警类型 = "其他故障", 报警详情 = "震盘缺料报警" ,关联的PLC地址 = 5301 },
  5256. new Alarm { 报警类型 = "其他故障", 报警详情 = "成品仓料满报警" ,关联的PLC地址 = 5302 },
  5257. new Alarm { 报警类型 = "其他故障", 报警详情 = "检测拍照超时报警" ,关联的PLC地址 = 5303 },
  5258. new Alarm { 报警类型 = "其他故障", 报警详情 = "检测拍照NG报警" ,关联的PLC地址 = 5304 },
  5259. new Alarm { 报警类型 = "其他故障", 报警详情 = "玻璃门打开报警" ,关联的PLC地址 = 5305 },
  5260. #endregion 第三组报警(其他故障)
  5261. };
  5262. DicAlarms_Cur.Add(GlobalContext.LineCode, keyValues1); // 这里使用线体代替工位
  5263. #endregion 第一个工站(这里使用线体代替工位)
  5264. # region 第二个工站-原来的写法(废弃)
  5265. //keyValues = new Dictionary<int, AlarmData[]>();
  5266. ////1
  5267. //dicAlarmName = new Dictionary<int, Alarm>();
  5268. //dicAlarmName.Add(0, new Alarm { Name = "M01衬套组模组X电机报警" });
  5269. //dicAlarmName.Add(1, new Alarm { Name = "M02衬套组模组Y电机报警" });
  5270. //dicAlarmName.Add(2, new Alarm { Name = "M03衬套组模组Z电机报警" });
  5271. //dicAlarmName.Add(3, new Alarm { Name = "M04衬套组模组U电机报警" });
  5272. //dicAlarmName.Add(4, new Alarm { Name = "M05外流线皮带电机报警" });
  5273. //alarmDatas = new AlarmData[dicAlarmName.Count];
  5274. //for (int i = 0; i < dicAlarmName.Count; i++)
  5275. //{
  5276. // alarmDatas[i] = new AlarmData();
  5277. // alarmDatas[i].Equipment_code = GlobalContext.LineCode + "-2";
  5278. // alarmDatas[i].AlarmDesc = dicAlarmName[i].Name;
  5279. // alarmDatas[i].AlarmName = dicAlarmName[i].Name;
  5280. // alarmDatas[i].AlarmType = 1;
  5281. //}
  5282. //keyValues.Add(1, alarmDatas);
  5283. ////2
  5284. //dicAlarmName = new Dictionary<int, Alarm>();
  5285. //dicAlarmName.Add(0, new Alarm { Name = "C01定位气缸故障" });
  5286. //dicAlarmName.Add(1, new Alarm { Name = "C02左推料气缸故障" });
  5287. //dicAlarmName.Add(2, new Alarm { Name = "C03右推料气缸故障" });
  5288. //dicAlarmName.Add(3, new Alarm { Name = "C04左压料气缸故障" });
  5289. //dicAlarmName.Add(4, new Alarm { Name = "C05右压料气缸故障" });
  5290. //dicAlarmName.Add(5, new Alarm { Name = "C06切料气缸故障" });
  5291. //dicAlarmName.Add(6, new Alarm { Name = "C07左入料吹气气缸故障" });
  5292. //dicAlarmName.Add(7, new Alarm { Name = "C08右入料吹气气缸故障" });
  5293. //alarmDatas = new AlarmData[dicAlarmName.Count];
  5294. //for (int i = 0; i < dicAlarmName.Count; i++)
  5295. //{
  5296. // alarmDatas[i] = new AlarmData();
  5297. // alarmDatas[i].Equipment_code = GlobalContext.LineCode + "-2";
  5298. // alarmDatas[i].AlarmDesc = dicAlarmName[i].Name;
  5299. // alarmDatas[i].AlarmName = dicAlarmName[i].Name;
  5300. // alarmDatas[i].AlarmType = 2;
  5301. //}
  5302. //keyValues.Add(2, alarmDatas);
  5303. ////3
  5304. //dicAlarmName = new Dictionary<int, Alarm>();
  5305. //dicAlarmName.Add(0, new Alarm { Name = "安全门报警" });
  5306. //dicAlarmName.Add(1, new Alarm { Name = "联机通信故障" });
  5307. //dicAlarmName.Add(2, new Alarm { Name = "连续NG报警" });
  5308. //dicAlarmName.Add(3, new Alarm { Name = "合格率低于设定值报警" });
  5309. //alarmDatas = new AlarmData[dicAlarmName.Count];
  5310. //for (int i = 0; i < dicAlarmName.Count; i++)
  5311. //{
  5312. // alarmDatas[i] = new AlarmData();
  5313. // alarmDatas[i].Equipment_code = GlobalContext.LineCode + "-3";
  5314. // alarmDatas[i].AlarmDesc = dicAlarmName[i].Name;
  5315. // alarmDatas[i].AlarmName = dicAlarmName[i].Name;
  5316. // alarmDatas[i].AlarmType = 3;
  5317. //}
  5318. //keyValues.Add(3, alarmDatas);
  5319. //DicAlarms.Add(2, keyValues);
  5320. #endregion 第二个工站-原来的写法(废弃)
  5321. }
  5322. }
  5323. }