Compare commits

..

62 Commits

Author SHA1 Message Date
Samuele E. Locatelli 2bb407d55c Merge remote-tracking branch 'origin/develop' into new/ThermoCamManager 2021-03-24 18:09:51 +01:00
Thermo_SIM 97dc1095b6 Added Id Piece on History 2021-03-24 14:24:23 +01:00
Thermo_SIM a090ef9fb2 FIx THermocam behaviour 2021-03-24 14:17:00 +01:00
Thermo_SIM c5c95f75ae Thickness 2021-03-24 12:38:15 +01:00
Thermo_SIM c95fb1806f FIx Caricatore view 2021-03-24 12:28:42 +01:00
Thermo_SIM d12d07c99e Fix UserLogin + IO 2021-03-24 12:16:21 +01:00
Samuele E. Locatelli 3103b7bba2 inizio vers 192 x fix visualizzazione IO 2021-03-24 11:45:03 +01:00
Samuele E. Locatelli b2932d927c Merge remote-tracking branch 'origin/develop' into new/ThermoCamManager 2021-03-24 11:25:04 +01:00
Thermo_SIM 68add4e08d Ottimizzazione Frontend 2021-03-24 11:24:33 +01:00
Samuele E. Locatelli 5585c11ef5 new rel start 2021-03-24 10:48:18 +01:00
Samuele E. Locatelli b9caa4ac74 setup serverConfig x SIM 2021-03-24 10:48:09 +01:00
Samuele E. Locatelli cde514eed8 refresh x test produzione 2021-03-24 09:29:37 +01:00
Samuele E. Locatelli fad45a5635 new rel 190 2021-03-24 09:29:26 +01:00
Samuele E. Locatelli 9bf2265082 pulizia riferimenti vers 0.8.1 --> 0.4.0 2021-03-24 09:29:18 +01:00
Samuele E. Locatelli e488619ae5 Merge remote-tracking branch 'origin/develop' into new/ThermoCamManager 2021-03-24 07:55:53 +01:00
Samuele E. Locatelli babd8b25da vers 189 semaforo unico 2021-03-24 07:55:40 +01:00
Thermo_SIM 5894cd63ce Check LastTakenImage 2021-03-24 07:33:58 +01:00
Samuele E. Locatelli 5a19d44b34 semaforo su confirm/cancel ricetta (strobe R798!) 2021-03-24 06:14:15 +01:00
Samuele E. Locatelli 577cbe5c9d start test new rel 2021-03-24 05:48:47 +01:00
Samuele E. Locatelli e881006857 gestione semafori x Reciper + Warmers 2021-03-23 21:47:31 +01:00
Samuele E. Locatelli 83fb0acfd0 helpers gestione semafori Recipe + Warmers 2021-03-23 21:47:21 +01:00
Samuele E. Locatelli 04b3588e7f lieve allungamento delay scrittura singole memorie ricetta 2021-03-23 21:46:54 +01:00
Samuele E. Locatelli c00e695c15 inizio nuova release 2021-03-23 19:34:02 +01:00
Samuele E. Locatelli c228c454f6 Merge remote-tracking branch 'origin/develop' into new/ThermoCamManager 2021-03-23 19:33:43 +01:00
Thermo_SIM e86495eab5 Added Thermocamera Takesnapshot 2021-03-23 17:31:13 +01:00
Samuele E. Locatelli 63e636cd36 fix base WebApi (NO dispose ncAdapter: non serve) 2021-03-23 12:49:04 +01:00
Samuele E. Locatelli 1458a4cf5d inserito force close 2021-03-23 12:43:55 +01:00
Samuele E. Locatelli 6cf7331081 Merge remote-tracking branch 'origin/develop' into new/ThermoCamManager 2021-03-23 12:09:26 +01:00
Samuele E. Locatelli 43402a785f aggiunti metodi dispose x WebAPI con ncAdapter 2021-03-23 12:09:10 +01:00
Thermo_SIM 88561778ce Fix Classes bitselector 2021-03-23 11:01:03 +01:00
Thermo_SIM 0d395fca33 Added LOG on Auth error 2021-03-23 10:48:17 +01:00
Samuele E. Locatelli 09fea8f0e3 start new rel 2021-03-23 10:47:34 +01:00
Thermo_SIM 42531aac49 Fix COnfirm IO 2021-03-23 10:23:24 +01:00
Thermo_SIM bbfc3ca64d Fix Caricatore 2021-03-23 09:18:02 +01:00
Thermo_SIM 50e76bd30c FIx Logs 2021-03-22 18:33:06 +01:00
Thermo_SIM 6f6559ce67 Fix Sheet read 2021-03-22 17:59:30 +01:00
Samuele E. Locatelli 5c2f69b8d2 fix serverconfig 2021-03-22 16:48:56 +01:00
Samuele E. Locatelli 0f7ce076f9 type 2021-03-22 16:18:47 +01:00
Samuele E. Locatelli 127b4ba1de new rel 185 2021-03-22 14:38:30 +01:00
Samuele E. Locatelli 9e2ee7d5b6 Merge branch 'develop' into new/ThermoCamManager 2021-03-22 14:38:10 +01:00
Thermo_SIM 2a0b3f7e72 Fix Frontend 2021-03-22 14:33:31 +01:00
Thermo_SIM 36dc4171e5 Added Migration 2021-03-22 14:24:34 +01:00
Thermo_SIM 29057c5431 Added TYpeval 2021-03-22 14:18:59 +01:00
Thermo_SIM a1336f9918 Merge branch 'Log_Lastre' into develop 2021-03-22 11:27:06 +01:00
Thermo_SIM 7ded45280f Fix THermocamera History 2021-03-22 11:26:33 +01:00
Thermo_SIM ef139a2365 Fix THermoprophet 2021-03-21 19:28:07 +01:00
Thermo_SIM fe6498f6ed Fix Vuoto Behaviour 2021-03-21 18:06:26 +01:00
Thermo_SIM 22ad46ab8c Fix bitselector 2021-03-21 17:57:19 +01:00
Thermo_SIM e098409b83 Fix COnfig FIle & Sheet cleaning 2021-03-19 22:52:17 +01:00
Thermo_SIM 083be20f02 Fix Frontend 2021-03-19 22:21:10 +01:00
Thermo_SIM f7ff6629ce Added NC Reading 2021-03-19 22:19:49 +01:00
Thermo_SIM 2a4c0e8335 Fix Frontend 2 2021-03-19 22:19:36 +01:00
Thermo_SIM bd1488bc02 FIx Frontend 2021-03-19 22:19:23 +01:00
Thermo_SIM bab9bf504a Removed ConsoleLog 2021-03-19 20:07:57 +01:00
Thermo_SIM c7f7c4f9c8 Added Frontend 2021-03-19 18:28:07 +01:00
Thermo_SIM 36e0927bd1 Backend 2021-03-19 18:00:03 +01:00
Thermo_SIM 7b132793d0 Third DB Commit 2021-03-19 17:26:34 +01:00
Thermo_SIM d01fcf7578 Second Commit 2021-03-19 17:11:18 +01:00
Thermo_SIM 539ed2508d First commit DB 2021-03-19 17:07:42 +01:00
Thermo_SIM cacae4eebf Fix pirometro in Dashboard 2021-03-19 16:40:07 +01:00
Thermo_SIM 34e31666cd Fix ricetta + Dashboard S 2021-03-19 16:05:30 +01:00
Samuele E. Locatelli 3b0dd98018 modifica meccanismo dispose FLIR 2021-03-19 10:11:43 +01:00
100 changed files with 20322 additions and 18824 deletions
+1 -1
View File
@@ -180,7 +180,7 @@
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
<Target Name="EnsureNuGetPackageBuildImports" BeforeTargets="PrepareForBuild">
<PropertyGroup>
<ErrorText>This project references NuGet package(s) that are missing on this computer. Use NuGet Package Restore to download them. For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}.</ErrorText>
<ErrorText>Questo progetto fa riferimento a uno o più pacchetti NuGet che non sono presenti in questo computer. Usare lo strumento di ripristino dei pacchetti NuGet per scaricarli. Per altre informazioni, vedere http://go.microsoft.com/fwlink/?LinkID=322105. Il file mancante è {0}.</ErrorText>
</PropertyGroup>
<Error Condition="!Exists('..\packages\cef.redist.x64.84.4.1\build\cef.redist.x64.props')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\cef.redist.x64.84.4.1\build\cef.redist.x64.props'))" />
<Error Condition="!Exists('..\packages\cef.redist.x86.84.4.1\build\cef.redist.x86.props')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\cef.redist.x86.84.4.1\build\cef.redist.x86.props'))" />
+4 -1
View File
@@ -4,6 +4,7 @@
<ncVendor>S7NET</ncVendor>
<!-- NO_NC/DEMO/FANUC/SIEMENS/OSAI/S7NET -->
<showNcHMI>false</showNcHMI>
<!--<ncIpAddress>192.168.139.1</ncIpAddress>-->
<ncIpAddress>192.168.0.102</ncIpAddress>
<ncPort>102</ncPort>
<machineModel>Thermo 2020</machineModel>
@@ -31,6 +32,8 @@
<CMSConnectReady>true</CMSConnectReady>
<maxAlarmsRows>50000</maxAlarmsRows>
<alarmToDelete>5000</alarmToDelete>
<maxSheetHistoryRows>10000</maxSheetHistoryRows>
<sheetHistoryToDelete>500</sheetHistoryToDelete>
</serverConfig>
<extSoftwares>
<software>
@@ -138,7 +141,7 @@
<thread name="expMan" value="30000" />
<thread name="functionEnab" value="300" />
<thread name="gauges" value="500" />
<thread name="m154" value="500" />
<thread name="m154" value="1000" />
<thread name="mCommands" value="250" />
<thread name="powerOn" value="500" />
<thread name="prodCycle" value="1000" />
@@ -42,6 +42,8 @@
<xs:element name="MTCApplicationName" type="xs:string" minOccurs="1" maxOccurs="1"/>
<xs:element name="maxAlarmsRows" type="xs:int" minOccurs="1" maxOccurs="1"/>
<xs:element name="alarmToDelete" type="xs:int" minOccurs="1" maxOccurs="1"/>
<xs:element name="maxSheetHistoryRows" type="xs:int" minOccurs="1" maxOccurs="1"/>
<xs:element name="sheetHistoryToDelete" type="xs:int" minOccurs="1" maxOccurs="1"/>
<xs:element name="CMSConnectReady" type="xs:boolean" minOccurs="1" maxOccurs="1"/>
</xs:all>
</xs:complexType>
@@ -1033,6 +1033,8 @@ namespace Thermo.Active.Config
MTCApplicationName = x.Element("MTCApplicationName").Value,
MaxAlarmsRows = Convert.ToInt32(x.Element("maxAlarmsRows").Value),
AlarmToDelete = Convert.ToInt32(x.Element("alarmToDelete").Value),
MaxSheetHistoryRows = Convert.ToInt32(x.Element("maxSheetHistoryRows").Value),
SheetHistoryToDelete = Convert.ToInt32(x.Element("sheetHistoryToDelete").Value),
CmsConnectReady = Convert.ToBoolean(x.Element("CMSConnectReady").Value)
}).FirstOrDefault();
+213 -75
View File
@@ -49,6 +49,7 @@ public static class ThreadsFunctions
public static int modulesRtCounter = 0;
public static int recipeRtCounter = 0;
public static bool reconnectionIsRunning = false;
public static bool forcetakeSnapshot = false;
#endregion Public Fields
@@ -193,34 +194,45 @@ public static class ThreadsFunctions
StatReset();
NcAdapter ncAdapter = new NcAdapter();
CmsError libraryError = NO_ERROR;
// Run loop until NC is connected
while (!ncAdapter.numericalControl.NC_IsConnected())
try
{
// Try reconnection
libraryError = ncAdapter.Connect();
if (libraryError.errorCode == CMS_ERROR_CODES.SIEMENS_ENVIRONMENT_NOT_FOUND || libraryError.errorCode == CMS_ERROR_CODES.SIEMENS_HMI_NOT_RUNNING || libraryError.errorCode == CMS_ERROR_CODES.OSAI_TT_FOLDER_NOT_FOUND)
ManageLibraryError(libraryError);
else if (libraryError.errorCode != CMS_ERROR_CODES.OK)
// Run loop until NC is connected
while (!ncAdapter.numericalControl.NC_IsConnected())
{
ncAdapter.Dispose();
// Try reconnection
libraryError = ncAdapter.Connect();
if (libraryError.errorCode == CMS_ERROR_CODES.SIEMENS_ENVIRONMENT_NOT_FOUND || libraryError.errorCode == CMS_ERROR_CODES.SIEMENS_HMI_NOT_RUNNING || libraryError.errorCode == CMS_ERROR_CODES.OSAI_TT_FOLDER_NOT_FOUND)
ManageLibraryError(libraryError);
else if (libraryError.errorCode != CMS_ERROR_CODES.OK)
{
ncAdapter.Dispose();
}
// Send status to UI
MessageServices.Current.Publish(SEND_NC_STATUS_UI, null, ncAdapter.numericalControl.NC_IsConnected());
// Send status to signalr
MessageServices.Current.Publish(SEND_NC_STATUS, null, ncAdapter.numericalControl.NC_IsConnected());
Thread.Sleep(1000);
}
// Send status to UI
MessageServices.Current.Publish(SEND_NC_STATUS_UI, null, ncAdapter.numericalControl.NC_IsConnected());
// Send status to signalr
MessageServices.Current.Publish(SEND_NC_STATUS, null, ncAdapter.numericalControl.NC_IsConnected());
if (!libraryError.IsError())
{
if (ServerStartupConfig.AutoOpenCmsClient)
StartCMSClient();
Thread.Sleep(1000);
// Start/Restart NC threads
ThreadsHandler.StartWorkers();
reconnectionIsRunning = false;
}
}
if (!libraryError.IsError())
catch (ThreadAbortException ex)
{
if (ServerStartupConfig.AutoOpenCmsClient)
StartCMSClient();
// Start/Restart NC threads
ThreadsHandler.StartWorkers();
reconnectionIsRunning = false;
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
@@ -326,6 +338,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
/// <summary>
@@ -345,6 +361,14 @@ public static class ThreadsFunctions
// avvio oggetto thermocam
ThermoCamComunicator TCCom = new ThermoCamComunicator(true);
Stopwatch sw = new Stopwatch();
forcetakeSnapshot = false;
RegistrationInfo takeReginfo = MessageServices.Current.Subscribe(TAKE_SNAPSHOT_THERMO, (a, b) =>
{
ThreadsFunctions.forcetakeSnapshot = true;
});
try
{
// Try connection
@@ -365,11 +389,13 @@ public static class ThreadsFunctions
if (libraryError.IsError())
ManageLibraryError(libraryError);
if (flirImageReq)
if (flirImageReq || forcetakeSnapshot)
{
forcetakeSnapshot = false;
bool done = false;
// if requested --> give ack!
ncAdapter.ManageFlirStrobe();
if (flirImageReq)
ncAdapter.ManageFlirStrobe();
// requesto photo from library
NcAdapter.lastThermoImage = TCCom.takePicture();
done = !string.IsNullOrEmpty(NcAdapter.lastThermoImage);
@@ -390,13 +416,20 @@ public static class ThreadsFunctions
}
// salvo dati temp sul PLC
ncAdapter.WriteRecipeWarmChTCamTempAct(actualTemp);
NcAdapter.lastImageTaken = DateTime.Now;
// give PLC strobe for uploaded Actual TEMP from image
ncAdapter.SendTCamImageReadyStrb();
if(flirImageReq)
ncAdapter.SendTCamImageReadyStrb();
MessageServices.Current.Publish(SEND_NEWTCAMIMAGE, null, NcAdapter.lastImageTaken);
}
}
// salvo status thermocam...
NcAdapter.cameraIsConnected = TCCom.CameraIsConnected;
}
else
RestoreConnection();
@@ -412,9 +445,13 @@ public static class ThreadsFunctions
catch (ThreadAbortException)
{
ncAdapter.Dispose();
// chiudo thermocam
TCCom.Dispose();
}
finally
{
MessageServices.Current.UnSubscribe(takeReginfo);
ncAdapter.Dispose();
// chiudo thermocam
TCCom.Dispose();
}
@@ -492,6 +529,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
public static void ManageWatchdog()
@@ -538,6 +579,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
public static void ReadAlarms()
@@ -582,6 +627,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
public static void ReadAreaData()
@@ -624,6 +673,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
/// <summary>
@@ -677,6 +730,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
/// <summary>
@@ -726,6 +783,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
public static void ReadEnabledFunctionality()
@@ -770,6 +831,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
public static void ReadExpiredMaintenances()
@@ -824,6 +889,11 @@ public static class ThreadsFunctions
}
catch (Exception ex)
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
@@ -868,6 +938,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
public static void ReadM154Data()
@@ -1042,6 +1116,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
public static void ReadMComandsData()
@@ -1088,6 +1166,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
public static void ReadModulesData()
@@ -1130,6 +1212,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
public static void ReadPowerOnData()
@@ -1172,6 +1258,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
public static void ReadProcessesPPStatus()
@@ -1218,6 +1308,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
public static void ReadProdCycleData()
@@ -1261,6 +1355,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
public static void ReadProdInfoData()
@@ -1304,6 +1402,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
public static void ReadProdPanelData()
@@ -1347,6 +1449,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
public static void ReadRecipeData()
@@ -1373,39 +1479,46 @@ public static class ThreadsFunctions
// Check if client is connected
if (ncAdapter.numericalControl.NC_IsConnected())
{
// Get new data from PLC
libraryError = ncAdapter.ReadRecipeData(onlyRt, false, out Dictionary<string, DTORecipeParam> currRecipe);
if (libraryError.IsError())
ManageLibraryError(libraryError);
MessageServices.Current.Publish(SEND_THERMO_RECIPE_FULL, null, currRecipe);
// ora gestisco la overview!
libraryError = ncAdapter.GetRecipeOverview(out Dictionary<RecipeSection, RecipeCatStatus> currOverview);
if (libraryError.IsError())
ManageLibraryError(libraryError);
MessageServices.Current.Publish(SEND_THERMO_RECIPE_OVERWIEW, null, currOverview);
// ora gestisco la lettura della overview di "modificata
DTORecipeStatus message = new DTORecipeStatus()
// controllo su redis che NON sia bloccata lettura ricetta..
if (!RedisController.getRecipeReadSem)
{
recipeName = NcAdapter.RecipeLiveData.RecipeName,
hasChanged = NcAdapter.RecipeLiveData.hasChanged
};
// Get new data from PLC
libraryError = ncAdapter.ReadRecipeData(onlyRt, false, out Dictionary<string, DTORecipeParam> currRecipe);
if (libraryError.IsError())
ManageLibraryError(libraryError);
MessageServices.Current.Publish(SEND_THERMO_RECIPE_CHANGED, null, message);
MessageServices.Current.Publish(SEND_THERMO_RECIPE_FULL, null, currRecipe);
// verifico se dal PLC è segnalato che i setpointHMI sono invalidati, nel qual caso INVIO
bool setpointHmiInvalidated = false;
libraryError = ncAdapter.checkSetpointInvalidated(out setpointHmiInvalidated);
if (setpointHmiInvalidated)
{
// ora gestisco l'ack della richiesta
libraryError = ncAdapter.doAckSetpointInvalidated();
// ora gestisco la overview!
libraryError = ncAdapter.GetRecipeOverview(out Dictionary<RecipeSection, RecipeCatStatus> currOverview);
if (libraryError.IsError())
ManageLibraryError(libraryError);
MessageServices.Current.Publish(SEND_THERMO_RECIPE_OVERWIEW, null, currOverview);
// ora gestisco la lettura della overview di "modificata
DTORecipeStatus message = new DTORecipeStatus()
{
recipeName = NcAdapter.RecipeLiveData.RecipeName,
hasChanged = NcAdapter.RecipeLiveData.hasChanged
};
MessageServices.Current.Publish(SEND_THERMO_RECIPE_CHANGED, null, message);
// verifico se dal PLC è segnalato che i setpointHMI sono invalidati, nel qual caso INVIO
bool setpointHmiInvalidated = false;
libraryError = ncAdapter.checkSetpointInvalidated(out setpointHmiInvalidated);
if (setpointHmiInvalidated)
{
// ora gestisco l'ack della richiesta
libraryError = ncAdapter.doAckSetpointInvalidated();
}
// pubblico booleana dei setpointHMI invalidati
MessageServices.Current.Publish(SEND_THERMO_RECIPE_SETPOINTHMI_CHANGED, null, setpointHmiInvalidated);
}
else
{
}
// pubblico booleana dei setpointHMI invalidati
MessageServices.Current.Publish(SEND_THERMO_RECIPE_SETPOINTHMI_CHANGED, null, setpointHmiInvalidated);
}
else
RestoreConnection();
@@ -1422,6 +1535,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
public static void ReadScadaData()
@@ -1467,6 +1584,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
public static void ReadUserSoftKeysData()
@@ -1511,6 +1632,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
public static void ReadWarmersData()
@@ -1528,33 +1653,38 @@ public static class ThreadsFunctions
bool useCache = false;
while (true)
{
sw.Restart();
// Check if client is connected
if (ncAdapter.numericalControl.NC_IsConnected())
// controllo su redis che NON sia bloccata lettura ricetta..
if (!RedisController.getWarmersReadSem)
{
if (cacheWarmers)
sw.Restart();
// Check if client is connected
if (ncAdapter.numericalControl.NC_IsConnected())
{
// every 10 reads all data...
useCache = (readCount != 0);
readCount++;
// ciclo resettato ogni 20
readCount = readCount % 20;
if (cacheWarmers)
{
// every 10 reads all data...
useCache = (readCount != 0);
readCount++;
// ciclo resettato ogni 20
readCount = readCount % 20;
}
// Get new data from PLC
libraryError = ncAdapter.ReadWarmers(useCache, out Dictionary<int, DTOWarmers> currWarmers);
if (libraryError.IsError())
ManageLibraryError(libraryError);
// pubblico
MessageServices.Current.Publish(SEND_THERMO_WARMERS_DATA, null, currWarmers);
}
// Get new data from PLC
libraryError = ncAdapter.ReadWarmers(useCache, out Dictionary<int, DTOWarmers> currWarmers);
if (libraryError.IsError())
ManageLibraryError(libraryError);
// pubblico
MessageServices.Current.Publish(SEND_THERMO_WARMERS_DATA, null, currWarmers);
else
RestoreConnection();
sw.Stop();
// Update thread timer
UpdateStat(MethodBase.GetCurrentMethod().Name, sw.ElapsedMilliseconds);
}
else
RestoreConnection();
sw.Stop();
// Update thread timer
UpdateStat(MethodBase.GetCurrentMethod().Name, sw.ElapsedMilliseconds);
// Wait
Thread.Sleep(CalcSleepTime(samplMsec("warmers"), (int)sw.ElapsedMilliseconds));
}
@@ -1563,6 +1693,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
public static void RestoreConnection()
@@ -1656,6 +1790,10 @@ public static class ThreadsFunctions
{
ncAdapter.Dispose();
}
finally
{
ncAdapter.Dispose();
}
}
public static void StartCMSClient()
-4
View File
@@ -38,10 +38,6 @@
<assemblyIdentity name="System.Runtime.InteropServices.RuntimeInformation" publicKeyToken="b03f5f7f11d50a3a" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-4.0.1.0" newVersion="4.0.1.0" />
</dependentAssembly>
<dependentAssembly>
<assemblyIdentity name="S7.Net" publicKeyToken="d5812d469e84c693" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-0.8.1.0" newVersion="0.8.1.0" />
</dependentAssembly>
</assemblyBinding>
</runtime>
</configuration>
-4
View File
@@ -57,10 +57,6 @@
<assemblyIdentity name="System.Runtime.InteropServices.RuntimeInformation" publicKeyToken="b03f5f7f11d50a3a" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-4.0.1.0" newVersion="4.0.1.0" />
</dependentAssembly>
<dependentAssembly>
<assemblyIdentity name="S7.Net" publicKeyToken="d5812d469e84c693" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-0.8.1.0" newVersion="0.8.1.0" />
</dependentAssembly>
</assemblyBinding>
</runtime>
</configuration>
@@ -0,0 +1,83 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Thermo.Active.Model.DatabaseModels;
using static Thermo.Active.Config.ServerConfig;
namespace Thermo.Active.Database.Controllers
{
public class HistorySheetsController : IDisposable
{
private DatabaseContext dbCtx;
public HistorySheetsController()
{
// Initialize database context
dbCtx = new DatabaseContext();
}
public void Dispose()
{
dbCtx.Dispose();
}
public HistorySheetModel Create(string recipe, short piece, float value1, float value2, float value3, ushort typeval)
{
HistorySheetModel mod = new HistorySheetModel()
{
DtEvent = DateTime.Now,
RecipeName = recipe,
NumDone = piece,
FirstVal = value1,
SecondVal = value2,
ThirdVal = value3,
TypeVal = typeval
};
// Add to database
dbCtx.HistorySheet.Add(mod);
// Commit changes
dbCtx.SaveChanges();
return mod;
}
public void Clean()
{
if (this.count() >= ServerStartupConfig.MaxSheetHistoryRows)
{
dbCtx.Database.ExecuteSqlCommand("DELETE FROM historysheets LIMIT {0}", ServerStartupConfig.SheetHistoryToDelete);
}
}
public List<HistorySheetModel> GetData(int start, int number)
{
// Get page numbers
return dbCtx
.HistorySheet
.OrderByDescending(x => x.DtEvent).Skip(start).Take(number).ToList();
}
public List<HistorySheetModel> GetData()
{
// Get page numbers
return dbCtx
.HistorySheet
.OrderByDescending(x => x.DtEvent).ToList();
}
public int count()
{
// Get page numbers
return dbCtx
.HistorySheet.Count();
}
}
}
@@ -21,6 +21,12 @@ namespace Thermo.Active.Database.Controllers
// Initialize database context
dbCtx = new DatabaseContext();
}
public void Dispose()
{
// Clear database context
dbCtx.Dispose();
}
#endregion Public Constructors
@@ -80,11 +86,6 @@ namespace Thermo.Active.Database.Controllers
return prodData;
}
public void Dispose()
{
// Clear database context
dbCtx.Dispose();
}
/// <summary>
/// Get record by NumDone
@@ -36,6 +36,12 @@ namespace Thermo.Active.Database.Controllers
private const string machineEventKpis = "Events:Kpis";
private const string machineMessagePath = "Events:Messages";
private const string thermoSemRecipe = "Thermo:Semaphore:All";
private const string thermoSemWarmers = "Thermo:Semaphore:All";
//private const string thermoSemRecipe = "Thermo:Semaphore:Recipe";
//private const string thermoSemWarmers = "Thermo:Semaphore:Warmers";
public static void WriteProductionNotification(uint ProductionProcess, string Notification)
{
string redisHash = redUtil.man.redHash(redisNotificationAddress).Replace("%NN%", ProductionProcess.ToString("00"));
@@ -246,5 +252,89 @@ namespace Thermo.Active.Database.Controllers
return true;
}
/// <summary>
/// Imposta semaforo Recipe
/// </summary>
/// <param name="doLock">true: imposto lock per 5 sec, false: tolgo lock (stringa vuota)</param>
/// <returns></returns>
public static bool setRecipeReadSem(bool doLock)
{
return setSemaphore(doLock, redUtil.man.redHash(thermoSemRecipe));
}
/// <summary>
/// Restituisce semaforo Recipe
/// </summary>
/// <returns></returns>
public static bool getRecipeReadSem
{
get
{
return getSemaphore(redUtil.man.redHash(thermoSemRecipe));
}
}
/// <summary>
/// Imposta semaforo Warmers
/// </summary>
/// <param name="doLock">true: imposto lock per 5 sec, false: tolgo lock (stringa vuota)</param>
/// <returns></returns>
public static bool setWarmersReadSem(bool doLock)
{
return setSemaphore(doLock, redUtil.man.redHash(thermoSemWarmers));
}
/// <summary>
/// Restituisce semaforo Warmers
/// </summary>
/// <returns></returns>
public static bool getWarmersReadSem
{
get
{
return getSemaphore(redUtil.man.redHash(thermoSemWarmers));
}
}
/// <summary>
/// Gestione generica SET semaforo
/// </summary>
/// <param name="doLock"></param>
/// <param name="redisHash"></param>
/// <returns></returns>
private static bool setSemaphore(bool doLock, string redisHash)
{
bool answ = true;
int ttlSec = 5;
string rawData = $"{DateTime.Now}";
try
{
if (doLock)
{
// imposto lock
answ = redUtil.man.setRSV(redisHash, rawData, ttlSec);
}
else
{
// metto empty string a 1 sec
answ = redUtil.man.setRSV(redisHash, "", 1);
}
}
catch
{ }
return answ;
}
/// <summary>
/// Gestione generica GET semafoto
/// </summary>
/// <param name="redisHash"></param>
/// <returns></returns>
private static bool getSemaphore(string redisHash)
{
bool answ = true;
string rawData = redUtil.man.getRSV(redisHash);
// se non nulla --> ho semaforo!
answ = !string.IsNullOrEmpty(rawData);
return answ;
}
}
}
+1 -1
View File
@@ -44,7 +44,7 @@ namespace Thermo.Active.Database
// thermo!
public DbSet<ProdInfoModel> ProdInfo { get; set; }
public DbSet<HistorySheetModel> HistorySheet { get; set; }
// Create migration string
public static string CONNECTION_STRING = "Server = " + "localhost" + "; Database=" + DATABASE_NAME + ";Uid=" + DATABASE_USER + ";Pwd=" + DATABASE_PWD + ";";
@@ -0,0 +1,29 @@
// <auto-generated />
namespace Thermo.Active.Database.Migrations
{
using System.CodeDom.Compiler;
using System.Data.Entity.Migrations;
using System.Data.Entity.Migrations.Infrastructure;
using System.Resources;
[GeneratedCode("EntityFramework.Migrations", "6.2.0-61023")]
public sealed partial class HistorySheets : IMigrationMetadata
{
private readonly ResourceManager Resources = new ResourceManager(typeof(HistorySheets));
string IMigrationMetadata.Id
{
get { return "202103191608500_HistorySheets"; }
}
string IMigrationMetadata.Source
{
get { return null; }
}
string IMigrationMetadata.Target
{
get { return Resources.GetString("Target"); }
}
}
}
@@ -0,0 +1,29 @@
namespace Thermo.Active.Database.Migrations
{
using System;
using System.Data.Entity.Migrations;
public partial class HistorySheets : DbMigration
{
public override void Up()
{
CreateTable(
"dbo.HistorySheets",
c => new
{
DtEvent = c.DateTime(nullable: false, precision: 0),
Recipe = c.String(unicode: false),
FirstVal = c.Single(nullable: false),
SecondVal = c.Single(nullable: false),
ThirdVal = c.Single(nullable: false),
})
.PrimaryKey(t => t.DtEvent);
}
public override void Down()
{
DropTable("dbo.HistorySheets");
}
}
}
File diff suppressed because one or more lines are too long
@@ -0,0 +1,29 @@
// <auto-generated />
namespace Thermo.Active.Database.Migrations
{
using System.CodeDom.Compiler;
using System.Data.Entity.Migrations;
using System.Data.Entity.Migrations.Infrastructure;
using System.Resources;
[GeneratedCode("EntityFramework.Migrations", "6.2.0-61023")]
public sealed partial class HistorySheetsCycle : IMigrationMetadata
{
private readonly ResourceManager Resources = new ResourceManager(typeof(HistorySheetsCycle));
string IMigrationMetadata.Id
{
get { return "202103191626072_HistorySheetsCycle"; }
}
string IMigrationMetadata.Source
{
get { return null; }
}
string IMigrationMetadata.Target
{
get { return Resources.GetString("Target"); }
}
}
}
@@ -0,0 +1,18 @@
namespace Thermo.Active.Database.Migrations
{
using System;
using System.Data.Entity.Migrations;
public partial class HistorySheetsCycle : DbMigration
{
public override void Up()
{
AddColumn("dbo.HistorySheets", "NumDone", c => c.Short(nullable: false));
}
public override void Down()
{
DropColumn("dbo.HistorySheets", "NumDone");
}
}
}
File diff suppressed because one or more lines are too long
@@ -0,0 +1,29 @@
// <auto-generated />
namespace Thermo.Active.Database.Migrations
{
using System.CodeDom.Compiler;
using System.Data.Entity.Migrations;
using System.Data.Entity.Migrations.Infrastructure;
using System.Resources;
[GeneratedCode("EntityFramework.Migrations", "6.2.0-61023")]
public sealed partial class addedTypeValHistory : IMigrationMetadata
{
private readonly ResourceManager Resources = new ResourceManager(typeof(addedTypeValHistory));
string IMigrationMetadata.Id
{
get { return "202103221323362_addedTypeValHistory"; }
}
string IMigrationMetadata.Source
{
get { return null; }
}
string IMigrationMetadata.Target
{
get { return Resources.GetString("Target"); }
}
}
}
@@ -0,0 +1,18 @@
namespace Thermo.Active.Database.Migrations
{
using System;
using System.Data.Entity.Migrations;
public partial class addedTypeValHistory : DbMigration
{
public override void Up()
{
AddColumn("dbo.HistorySheets", "TypeVal", c => c.Int(nullable: false));
}
public override void Down()
{
DropColumn("dbo.HistorySheets", "TypeVal");
}
}
}
File diff suppressed because one or more lines are too long
@@ -124,6 +124,7 @@
<ItemGroup>
<Compile Include="Controllers\AlarmsController.cs" />
<Compile Include="Controllers\FunctionsAccessController.cs" />
<Compile Include="Controllers\HistorySheetsController.cs" />
<Compile Include="Controllers\ProdInfoController.cs" />
<Compile Include="Controllers\MachinesController.cs" />
<Compile Include="Controllers\MaintenancesController.cs" />
@@ -158,6 +159,18 @@
<Compile Include="Migrations\202102171753226_Added_ThermoImage_prodInfo.Designer.cs">
<DependentUpon>202102171753226_Added_ThermoImage_prodInfo.cs</DependentUpon>
</Compile>
<Compile Include="Migrations\202103191608500_HistorySheets.cs" />
<Compile Include="Migrations\202103191608500_HistorySheets.Designer.cs">
<DependentUpon>202103191608500_HistorySheets.cs</DependentUpon>
</Compile>
<Compile Include="Migrations\202103191626072_HistorySheetsCycle.cs" />
<Compile Include="Migrations\202103191626072_HistorySheetsCycle.Designer.cs">
<DependentUpon>202103191626072_HistorySheetsCycle.cs</DependentUpon>
</Compile>
<Compile Include="Migrations\202103221323362_addedTypeValHistory.cs" />
<Compile Include="Migrations\202103221323362_addedTypeValHistory.Designer.cs">
<DependentUpon>202103221323362_addedTypeValHistory.cs</DependentUpon>
</Compile>
<Compile Include="Migrations\Configuration.cs" />
<Compile Include="Properties\AssemblyInfo.cs" />
<Compile Include="Redis\redUtil.cs" />
@@ -212,6 +225,15 @@
<EmbeddedResource Include="Migrations\202102171753226_Added_ThermoImage_prodInfo.resx">
<DependentUpon>202102171753226_Added_ThermoImage_prodInfo.cs</DependentUpon>
</EmbeddedResource>
<EmbeddedResource Include="Migrations\202103191608500_HistorySheets.resx">
<DependentUpon>202103191608500_HistorySheets.cs</DependentUpon>
</EmbeddedResource>
<EmbeddedResource Include="Migrations\202103191626072_HistorySheetsCycle.resx">
<DependentUpon>202103191626072_HistorySheetsCycle.cs</DependentUpon>
</EmbeddedResource>
<EmbeddedResource Include="Migrations\202103221323362_addedTypeValHistory.resx">
<DependentUpon>202103221323362_addedTypeValHistory.cs</DependentUpon>
</EmbeddedResource>
</ItemGroup>
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
</Project>
@@ -18,5 +18,9 @@ namespace Thermo.Active.Model.ConfigModels
public int MaxAlarmsRows { get; set; }
public int AlarmToDelete { get; set; }
public int MaxSheetHistoryRows { get; set; }
public int SheetHistoryToDelete { get; set; }
}
}
+2
View File
@@ -23,6 +23,7 @@ namespace Thermo.Active.Model
public const string AXES_CONFIG_PATH = CONFIG_DIRECTORY + "axesConfig.xml";
public const string AXES_CONFIG_SCHEMA_PATH = RESOURCE_DIRECTORY + @"axesConfigValidator.xsd";
public const string BROADCAST_DATA = "BROADCAST_DATA";
public const string TAKE_SNAPSHOT_THERMO = "TAKE_SNAPSHOT_THERMO";
// File paths
public const string CLIENT_EXE_NAME = @"Active_Client.exe";
@@ -104,6 +105,7 @@ namespace Thermo.Active.Model
public const string SEND_AXIS_INFO = "SEND_AXIS_INFO";
public const string SEND_CHANNELS_IO_DATA = "SEND_CHANNELS_IO_DATA";
public const string SEND_NEWTCAMIMAGE = "SEND_NEWTCAMIMAGE";
public const string SEND_CMSCONNECT_GW_REBOOT_STATUS = "SEND_CMSCONNECT_GW_REBOOT_STATUS";
public const string SEND_ERROR_TO_UI = "SEND_ERROR_TO_UI";
public const string SEND_EXPIRED_MAINTENANCES_DATA = "SEND_EXPIRED_MAINTENANCES_DATA";
@@ -40,6 +40,11 @@ namespace Thermo.Active.Model.DTOModels.ThWarmers
/// </summary>
public bool ThermoOptionActive { get; set; } = false;
/// <summary>
/// Data ultima acquisizione
/// </summary>
public DateTime LastTakenImage { get; set; } = new DateTime(0);
#endregion Public Properties
#region Public Methods
@@ -64,7 +69,9 @@ namespace Thermo.Active.Model.DTOModels.ThWarmers
return false;
if (RangeTemperature != item.RangeTemperature)
return false;
if (LastTakenImage != item.LastTakenImage)
return false;
return true;
}
@@ -0,0 +1,38 @@
using System;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
namespace Thermo.Active.Model.DatabaseModels
{
[Table("HistorySheets")]
public class HistorySheetModel
{
#region Public Properties
[Key]
[DatabaseGenerated(DatabaseGeneratedOption.None)]
[Column("DtEvent", Order = 0)]
public DateTime DtEvent { get; set; }
[Column("Recipe")]
public string RecipeName { get; set; }
[Column("NumDone")]
public short NumDone { get; set; }
[Column("FirstVal")]
public float FirstVal { get; set; }
[Column("SecondVal")]
public float SecondVal { get; set; }
[Column("ThirdVal")]
public float ThirdVal { get; set; }
[Column("TypeVal")]
public int TypeVal { get; set; }
#endregion Public Properties
}
}
@@ -85,6 +85,7 @@
<Compile Include="DatabaseModels\AlarmNoteModel.cs" />
<Compile Include="DatabaseModels\AlarmOccurrencesModel.cs" />
<Compile Include="DatabaseModels\AlarmUserModel.cs" />
<Compile Include="DatabaseModels\HistorySheetModel.cs" />
<Compile Include="DatabaseModels\FavoriteUserSoftKeyModel.cs" />
<Compile Include="DatabaseModels\FunctionAccessModel.cs" />
<Compile Include="ConfigModels\MessageModel.cs" />
+102 -1
View File
@@ -140,6 +140,11 @@ namespace Thermo.Active.NC
/// </summary>
public static bool cameraIsConnected = false;
/// <summary>
/// Indica se la FLIR camera è connessa
/// </summary>
public static DateTime lastImageTaken = new DateTime(0);
#endregion Public Fields
#region Public Constructors
@@ -470,10 +475,16 @@ namespace Thermo.Active.NC
// solo x S7...
if (NcConfig.NcVendor == NC_VENDOR.S7NET)
{
// registro in redis blocco x lettura ricetta...
RedisController.setRecipeReadSem(true);
// call NC for update
CmsError libraryError = numericalControl.PLC_WRecipeEdit(confirmUpdate);
if (libraryError.IsError())
return libraryError;
// tolgo blocco x lettura ricetta...
RedisController.setRecipeReadSem(false);
}
else
{
@@ -1759,10 +1770,16 @@ namespace Thermo.Active.NC
{
if (NcFileAdapter.RecipeLiveData.ChannelSetpoints != null)
{
// registro in redis blocco x lettura ricetta...
RedisController.setRecipeReadSem(true);
// se si in questo caso scrivo configurazione...
WriteRecipeWarmConfig();
// Ack !
libraryError = numericalControl.PLC_WAckConfRiskRequest();
// tolgo in redis blocco x lettura ricetta...
RedisController.setRecipeReadSem(false);
}
}
if (ThermoReqConfRecipeStr)
@@ -1790,8 +1807,12 @@ namespace Thermo.Active.NC
return NOT_FOUND_ERROR;
}
}
// registro in redis blocco x lettura ricetta...
RedisController.setRecipeReadSem(true);
// se si in questo caso scrivo configurazione attuale...
WriteRecipeParams(updtRecipe, nMaxParamWrite, delayParamWrite);
// tolgo in redis blocco x lettura ricetta...
RedisController.setRecipeReadSem(false);
using (UserSoftkeysController controller = new UserSoftkeysController())
{
@@ -1808,6 +1829,9 @@ namespace Thermo.Active.NC
newRisk.Add(item.Key, item.Value);
}
// registro in redis blocco x lettura ricetta...
RedisController.setRecipeReadSem(true);
// write to PLC SetPointHMI (%)
libraryError = WriteRecipeWarmChSetpHMI(newRisk);
if (libraryError.IsError())
@@ -1822,6 +1846,9 @@ namespace Thermo.Active.NC
libraryError = ConfirmRecipeData(true);
if (libraryError.IsError())
return libraryError;
// tolgo in redis blocco x lettura ricetta...
RedisController.setRecipeReadSem(true);
}
}
}
@@ -2515,7 +2542,7 @@ namespace Thermo.Active.NC
{
imgName = "UNDEFINED";
}
prodInfoController.Create(pInfoRaw.NumTarget, pInfoRaw.NumDone, pInfoRaw.TimeWarm, pInfoRaw.TimeVent, pInfoRaw.TimeVacuum, pInfoRaw.TimeCycleGross, pInfoRaw.TimeCycleNet, pInfoRaw.MaterialTempEndWarm, pInfoRaw.MaterialTempEndVent, pInfoRaw.MoldTemp, pInfoRaw.VacuumReadVal, pInfoRaw.MouldEnergyOUT, pInfoRaw.MouldEnergyIN, false, pInfoRaw.ThermoImage);
prodInfoController.Create(pInfoRaw.NumTarget, pInfoRaw.NumDone, pInfoRaw.TimeWarm, pInfoRaw.TimeVent, pInfoRaw.TimeVacuum, pInfoRaw.TimeCycleGross, pInfoRaw.TimeCycleNet, pInfoRaw.MaterialTempEndWarm, pInfoRaw.MaterialTempEndVent, pInfoRaw.MoldTemp, pInfoRaw.VacuumReadVal, pInfoRaw.MouldEnergyOUT, pInfoRaw.MouldEnergyIN, false, imgName);
// indico di rileggere il DB...
forceProdPanelDbReload = true;
}
@@ -2561,6 +2588,26 @@ namespace Thermo.Active.NC
lastProdStart = DateTime.Now;
}
ThermoModels.HistorySheet sheetRaw = new ThermoModels.HistorySheet();
libraryError = numericalControl.PLC_RHistorySheets(ref sheetRaw);
if (libraryError.IsError())
return libraryError;
if (sheetRaw.newData)
{
using (HistorySheetsController HSC = new HistorySheetsController())
{
HSC.Create(NcFileAdapter.RecipeLiveData.RecipeName, sheetRaw.IdPiece, (float) sheetRaw.Value1, (float) sheetRaw.Value2, (float) sheetRaw.Value3,sheetRaw.TypeVal);
// manage strobe/ack!
libraryError = numericalControl.PLC_WAckHistorySheets();
if (libraryError.IsError())
return libraryError;
}
}
return libraryError;
}
@@ -3172,6 +3219,9 @@ namespace Thermo.Active.NC
};
// controllo se connessa
currTCamData.ThermoCamConnected = cameraIsConnected;
// DataOra ultima immagine scattata
currTCamData.LastTakenImage = lastImageTaken;
}
return libraryError;
}
@@ -3393,8 +3443,14 @@ namespace Thermo.Active.NC
/// <returns></returns>
public CmsError SetTCamActiv(bool enableTCam)
{
// registro in redis blocco x lettura ricetta...
RedisController.setWarmersReadSem(true);
CmsError libraryError = numericalControl.PLC_WTCamActiv(enableTCam);
// tolgo in redis blocco x lettura ricetta...
RedisController.setWarmersReadSem(false);
return libraryError;
}
@@ -3405,8 +3461,14 @@ namespace Thermo.Active.NC
/// <returns></returns>
public CmsError SetTCamMode(bool enableTCam)
{
// registro in redis blocco x lettura ricetta...
RedisController.setWarmersReadSem(true);
CmsError libraryError = numericalControl.PLC_WTCamMode(enableTCam);
// tolgo in redis blocco x lettura ricetta...
RedisController.setWarmersReadSem(false);
return libraryError;
}
@@ -3641,8 +3703,15 @@ namespace Thermo.Active.NC
/// <returns></returns>
public CmsError WriteRecipeParams(Dictionary<string, DTORecipeParam> updtRecipe, int nMaxParamWrite, int delayParamWrite)
{
// registro in redis blocco x lettura ricetta...
RedisController.setRecipeReadSem(true);
CmsError libraryError = WriteRecipeParametersToPLC(updtRecipe, nMaxParamWrite, delayParamWrite);
// tolgo blocco x lettura ricetta...
RedisController.setRecipeReadSem(false);
return libraryError;
}
@@ -3653,8 +3722,15 @@ namespace Thermo.Active.NC
/// <returns></returns>
public CmsError WriteRecipeWarmChSetpHMI(Dictionary<int, int> updtSetpHmi)
{
// registro in redis blocco x lettura warmers...
RedisController.setWarmersReadSem(true);
CmsError libraryError = numericalControl.PLC_WWarmerChSetpHmi(updtSetpHmi);
// tolgo blocco x lettura warmers...
RedisController.setWarmersReadSem(false);
return libraryError;
}
@@ -3665,8 +3741,14 @@ namespace Thermo.Active.NC
/// <returns></returns>
public CmsError WriteRecipeWarmChTCamEnab(Dictionary<int, bool> actualStates)
{
// registro in redis blocco x lettura warmers...
RedisController.setWarmersReadSem(true);
CmsError libraryError = numericalControl.PLC_WWarmerChTCamEnab(actualStates);
// tolgo blocco x lettura warmers...
RedisController.setWarmersReadSem(false);
return libraryError;
}
@@ -3677,8 +3759,14 @@ namespace Thermo.Active.NC
/// <returns></returns>
public CmsError WriteRecipeWarmChTCamTempAct(Dictionary<int, double> actualTemp)
{
// registro in redis blocco x lettura warmers...
RedisController.setWarmersReadSem(true);
CmsError libraryError = numericalControl.PLC_WWarmerChTCamTempAct(actualTemp);
// tolgo blocco x lettura warmers...
RedisController.setWarmersReadSem(false);
return libraryError;
}
@@ -3689,8 +3777,14 @@ namespace Thermo.Active.NC
/// <returns></returns>
public CmsError WriteRecipeWarmChTCamTempSet(Dictionary<int, double> referenceTemp)
{
// registro in redis blocco x lettura warmers...
RedisController.setWarmersReadSem(true);
CmsError libraryError = numericalControl.PLC_WWarmerChTCamTempSet(referenceTemp);
// tolgo blocco x lettura warmers...
RedisController.setWarmersReadSem(false);
return libraryError;
}
@@ -3704,6 +3798,9 @@ namespace Thermo.Active.NC
Dictionary<int, int> newData = new Dictionary<int, int>();
CmsError libraryError = NO_ERROR;
// registro in redis blocco x lettura warmers...
RedisController.setWarmersReadSem(true);
// scrivo l'abilitazione dei canali...
foreach (var item in RiskBoardConfig)
{
@@ -3765,6 +3862,10 @@ namespace Thermo.Active.NC
numericalControl.PLC_WWarmerChTCamEnab(resetTCamEnab);
numericalControl.PLC_WWarmerChTCamTempAct(resetTCamTemp);
numericalControl.PLC_WWarmerChTCamTempSet(resetTCamTemp);
// tolgo blocco x lettura warmers...
RedisController.setWarmersReadSem(false);
// esce
return libraryError;
}
-4
View File
@@ -38,10 +38,6 @@
<assemblyIdentity name="System.Runtime.InteropServices.RuntimeInformation" publicKeyToken="b03f5f7f11d50a3a" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-4.0.1.0" newVersion="4.0.1.0" />
</dependentAssembly>
<dependentAssembly>
<assemblyIdentity name="S7.Net" publicKeyToken="d5812d469e84c693" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-0.8.1.0" newVersion="0.8.1.0" />
</dependentAssembly>
</assemblyBinding>
</runtime>
</configuration>
-4
View File
@@ -38,10 +38,6 @@
<assemblyIdentity name="System.Runtime.InteropServices.RuntimeInformation" publicKeyToken="b03f5f7f11d50a3a" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-4.0.1.0" newVersion="4.0.1.0" />
</dependentAssembly>
<dependentAssembly>
<assemblyIdentity name="S7.Net" publicKeyToken="d5812d469e84c693" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-0.8.1.0" newVersion="0.8.1.0" />
</dependentAssembly>
</assemblyBinding>
</runtime>
</configuration>
@@ -47,6 +47,10 @@ namespace Thermo.Active.Utils
{
Log.Info(message);
}
public static void LogDebug(string message)
{
Log.Debug(message);
}
public static void LogWarning(string message)
{
+2
View File
@@ -430,4 +430,6 @@
<axis_info_position>In posizione:</axis_info_position>
<axis_info_error>In errore:</axis_info_error>
<axis_info_brakealm>Allarme test freno:</axis_info_brakealm>
<bitselect_select_none>Nessuno</bitselect_select_none>
<bitselect_select_all>Tutti</bitselect_select_all>
</root>
+2
View File
@@ -430,4 +430,6 @@
<axis_info_position>In Position:</axis_info_position>
<axis_info_error>In Error:</axis_info_error>
<axis_info_brakealm>Brake Test Alarm:</axis_info_brakealm>
<bitselect_select_none>None</bitselect_select_none>
<bitselect_select_all>All</bitselect_select_all>
</root>
+1 -5
View File
@@ -15,7 +15,7 @@
<add key="ClientSettingsProvider.ServiceUri" value="" />
<add key="ServerServiceName" value="MariaDB" />
<add key="nMaxParamWrite" value="5" />
<add key="delayParamWrite" value="5" />
<add key="delayParamWrite" value="10" />
<add key="ewmaPar100" value="40" />
<add key="flirSwapXY" value="true" />
<add key="cacheWarmers" value="false" />
@@ -115,10 +115,6 @@
<assemblyIdentity name="System.Runtime.InteropServices.RuntimeInformation" publicKeyToken="b03f5f7f11d50a3a" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-4.0.1.0" newVersion="4.0.1.0" />
</dependentAssembly>
<dependentAssembly>
<assemblyIdentity name="S7.Net" publicKeyToken="d5812d469e84c693" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-0.8.1.0" newVersion="0.8.1.0" />
</dependentAssembly>
</assemblyBinding>
</runtime>
<connectionStrings>
@@ -8,6 +8,7 @@ using System.Security.Principal;
using Thermo.Active.Config;
using Thermo.Active.Database.Controllers;
using Thermo.Active.Model.DatabaseModels;
using Thermo.Active.Utils;
using static Thermo.Active.Config.ServerConfig;
using static Thermo.Active.Listeners.SignalRStaticObjects;
using static Thermo.Active.Model.Constants;
@@ -28,7 +29,11 @@ namespace Thermo.Active.Attributes
// Find user session on this machine
SessionModel session = sessionsController.FindSessionByToken(token);
if (session == null)
{
ThermoActiveLogger.LogError($"SignalRAuthorizeAttribute | AuthorizeHubConnection | session == null");
return false;
}
}
return base.AuthorizeHubConnection(hubDescriptor, request);
@@ -39,11 +44,16 @@ namespace Thermo.Active.Attributes
var connectionId = hubIncomingInvokerContext.Hub.Context.ConnectionId;
var request = hubIncomingInvokerContext.Hub.Context.Request;
var token = request.QueryString.Get("Authorization");
if (!string.IsNullOrEmpty(token))
{
// check authorization
if (!CheckAuthorization(FunctionAccess, token, out int machineId, out int userId))
{
ThermoActiveLogger.LogError($"SignalRAuthorizeAttribute | AuthorizeHubMethodInvocation | CheckAuthorization == false");
return false;
}
var claims = new ClaimsIdentity(AUTHENTICATION_TYPE);
claims.AddClaim(new Claim(USER_ID_KEY, userId.ToString()));
@@ -66,11 +76,17 @@ namespace Thermo.Active.Attributes
// Find user session on this machine
SessionModel session = sessionsController.FindSessionByToken(token);
if (session == null)
{
ThermoActiveLogger.LogError($"SignalRAuthorizeAttribute | CheckAuthorization | session == null");
return false;
}
// Check if the machine is the same where the user logged in
if (session.MachineUser.MachineId != MachineConfig.MachineId)
{
ThermoActiveLogger.LogError($"SignalRAuthorizeAttribute | CheckAuthorization | session.MachineUser.MachineId != MachineConfig.MachineId | " + session.MachineUser.MachineId + "," + MachineConfig.MachineId);
return false;
}
machineId = session.MachineUser.MachineId;
userId = session.MachineUser.UserId;
@@ -91,12 +107,18 @@ namespace Thermo.Active.Attributes
if (Action == ACTIONS.READ)
{ // Check read permissions
if (functionAccess.ReadLevelMin > machineUser.Role.Level)
{
ThermoActiveLogger.LogError($"SignalRAuthorizeAttribute | CheckAuthorization | functionAccess.ReadLevelMin > machineUser.Role.Level | " + functionAccess.ReadLevelMin + "," + machineUser.Role.Level);
return false; // Not authorized
}
}
else
{ // Check write permissions
if (functionAccess.WriteLevelMin > machineUser.Role.Level)
{
ThermoActiveLogger.LogError($"SignalRAuthorizeAttribute | CheckAuthorization | functionAccess.WriteLevelMin > machineUser.Role.Level | " + functionAccess.WriteLevelMin + "," + machineUser.Role.Level);
return false; // Not authorized
}
}
// Check if PLC bit exists
@@ -105,13 +127,21 @@ namespace Thermo.Active.Attributes
// Check if functionality is enabled by PLC
var functionalityIsEnabled = LastRuntimeFunctionality.Where(x => x.Name == functionName).FirstOrDefault();
if (functionalityIsEnabled == null || functionalityIsEnabled.Enabled == false)
return false;
{
ThermoActiveLogger.LogError($"SignalRAuthorizeAttribute | CheckAuthorization | functionalityIsEnabled == null || functionalityIsEnabled.Enabled == false | " + functionalityIsEnabled + "," + functionalityIsEnabled.Enabled);
return false; // Not authorized
}
}
}
else
{
ThermoActiveLogger.LogError($"SignalRAuthorizeAttribute | CheckAuthorization | functionAccess != null && ServerConfigController.CheckAreaStatus(functionAccess.Area) | " + functionAccess + "," + functionAccess.Area);
return false;
}
// Authorized
ThermoActiveLogger.LogInfo($"SignalRAuthorizeAttribute | CheckAuthorization | Authorized | ");
return true;
}
}
@@ -22,12 +22,14 @@ using static Thermo.Active.Model.Constants;
namespace Thermo.Active.Controllers.WebApi
{
[RoutePrefix("api/maintenance_manager")]
public class ApiMaintenanceController : ApiController
public class ApiMaintenanceController : aBaseApiController // ApiController
{
#if false
/// <summary>
/// Oggetto adapter condiviso da WebAPI
/// </summary>
protected static NcAdapter ncAdapter = new NcAdapter();
protected static NcAdapter ncAdapter = new NcAdapter();
#endif
[Route("maintenances"), HttpGet]
[WebApiAuthorize(FunctionAccess = FUNCTIONALITY_NAMES.MAINTENANCE, Action = ACTIONS.READ)]
@@ -10,7 +10,7 @@ using static Thermo.Active.Model.Constants;
namespace Thermo.Active.Controllers.WebApi
{
[RoutePrefix("api/authorization")]
public class AuthorizationController : ApiController
public class AuthorizationController : ApiController
{
[Route("functions"), HttpGet]
[WebApiAuthorize(FunctionAccess = FUNCTIONALITY_NAMES.GENERAL, Action = ACTIONS.READ)]
@@ -13,12 +13,14 @@ using static Thermo.Active.Model.Constants;
namespace Thermo.Active.Controllers.WebApi
{
[RoutePrefix("api/user_softkey")]
public class FavoriteUserSoftkeyController : ApiController
public class FavoriteUserSoftkeyController : aBaseApiController // ApiController
{
#if false
/// <summary>
/// Oggetto adapter condiviso da WebAPI
/// </summary>
protected static NcAdapter ncAdapter = new NcAdapter();
protected static NcAdapter ncAdapter = new NcAdapter();
#endif
[Route("favorite"), HttpGet]
@@ -12,12 +12,14 @@ using static Thermo.Active.Utils.LanguageController;
namespace Thermo.Active.Controllers.WebApi
{
[RoutePrefix("api/language")]
public class LanguageController : ApiController
public class LanguageController : aBaseApiController // ApiController
{
#if false
/// <summary>
/// Oggetto adapter condiviso da WebAPI
/// </summary>
protected static NcAdapter ncAdapter = new NcAdapter();
protected static NcAdapter ncAdapter = new NcAdapter();
#endif
[Route("languages"), HttpGet]
public IHttpActionResult GetLanguageList()
@@ -8,12 +8,14 @@ using Thermo.Active.Utils;
namespace Thermo.Active.Controllers.WebApi
{
[RoutePrefix("api/ModBlock")]
public class ModulesController : ApiController
public class ModulesController : aBaseApiController // ApiController
{
#if false
/// <summary>
/// Oggetto adapter condiviso da WebAPI
/// </summary>
protected static NcAdapter ncAdapter = new NcAdapter();
protected static NcAdapter ncAdapter = new NcAdapter();
#endif
[Route("current"), HttpGet]
public IHttpActionResult GetCurrentModules()
@@ -8,13 +8,15 @@ using static Thermo.Active.Model.Constants;
namespace Thermo.Active.Controllers.WebApi
{
[RoutePrefix("api/nc")]
public class NcApiController : ApiController
public class NcApiController : aBaseApiController // ApiController
{
#if false
/// <summary>
/// Oggetto adapter condiviso da WebAPI
/// </summary>
protected static NcAdapter ncAdapter = new NcAdapter();
#endif
[Route("generic_data"), HttpGet]
[WebApiAuthorize(FunctionAccess = FUNCTIONALITY_NAMES.NC_DATA, Action = ACTIONS.READ)]
public IHttpActionResult GetNcGenericData()
@@ -11,13 +11,16 @@ using static Thermo.Active.Model.Constants;
namespace Thermo.Active.Controllers.WebApi
{
[RoutePrefix("api/prod")]
public class ProdController : ApiController
public class ProdController : aBaseApiController //ApiController
{
#if false
/// <summary>
/// Oggetto adapter condiviso da WebAPI
/// </summary>
protected static NcAdapter ncAdapter = new NcAdapter();
#endif
/// <summary>
/// Request mode SETUP
/// </summary>
@@ -26,12 +26,14 @@ using static Thermo.Active.Model.Constants;
namespace Thermo.Active.Controllers.WebApi
{
[RoutePrefix("api/recipe")]
public class RecipeController : ApiController
public class RecipeController : aBaseApiController // ApiController
{
#if false
/// <summary>
/// Oggetto adapter condiviso da WebAPI
/// </summary>
protected static NcAdapter ncAdapter = new NcAdapter();
protected static NcAdapter ncAdapter = new NcAdapter();
#endif
[Route("overview"), HttpGet]
public IHttpActionResult GetOverview()
@@ -699,6 +701,7 @@ namespace Thermo.Active.Controllers.WebApi
}
// copy data to PLC
checkError = ncAdapter.ReadFullRecipe(out Dictionary<string, DTORecipeParam> prevRecipe);
if (checkError.IsError())
@@ -13,12 +13,14 @@ namespace Thermo.Active.Controllers.WebApi
{
[RoutePrefix("api/scada")]
public class ScadaController : ApiController
public class ScadaController : aBaseApiController // ApiController
{
#if false
/// <summary>
/// Oggetto adapter condiviso da WebAPI
/// </summary>
protected static NcAdapter ncAdapter = new NcAdapter();
protected static NcAdapter ncAdapter = new NcAdapter();
#endif
[Route("list"), HttpGet]
public IHttpActionResult GetScadaList()
@@ -8,12 +8,14 @@ using Thermo.Active.Utils;
namespace Thermo.Active.Controllers.WebApi
{
[RoutePrefix("api/starred_softkey")]
public class StarredUserSoftKeyController : ApiController
public class StarredUserSoftKeyController : aBaseApiController // ApiController
{
#if false
/// <summary>
/// Oggetto adapter condiviso da WebAPI
/// </summary>
protected static NcAdapter ncAdapter = new NcAdapter();
protected static NcAdapter ncAdapter = new NcAdapter();
#endif
[Route("get"), HttpGet]
public IHttpActionResult GetStarredUserSoftkey()
@@ -15,6 +15,7 @@ using System.Windows.Media.Animation;
using TeamDev.SDK.MVVM;
using Thermo.Active.Config;
using Thermo.Active.Database.Controllers;
using Thermo.Active.Model.DatabaseModels;
using Thermo.Active.Model.DTOModels;
using Thermo.Active.Model.DTOModels.ThIO;
using Thermo.Active.Model.DTOModels.ThRecipe;
@@ -28,12 +29,15 @@ using static Thermo.Active.Model.Constants;
namespace Thermo.Active.Controllers.WebApi
{
[RoutePrefix("api/underthehood")]
public class UnderTheHoodController : ApiController
public class UnderTheHoodController : aBaseApiController // ApiController
{
#if false
/// <summary>
/// Oggetto adapter condiviso da WebAPI
/// </summary>
protected static NcAdapter ncAdapter = new NcAdapter();
protected static NcAdapter ncAdapter = new NcAdapter();
#endif
[ResponseType(typeof(DTOCycleLog))]
[Route("CycleLogRefresh"), HttpGet]
@@ -364,5 +368,41 @@ namespace Thermo.Active.Controllers.WebApi
// ritorno solo fatto!
return Ok(expires);
}
[ResponseType(typeof(List<HistorySheetModel>))]
[Route("SheetHistory"), HttpGet]
public IHttpActionResult GetSheetHistory()
{
using (HistorySheetsController hsc = new HistorySheetsController())
{
List<HistorySheetModel> models = hsc.GetData();
return Ok(models);
}
}
[ResponseType(typeof(List<HistorySheetModel>))]
[Route("SheetHistoryFiltered"), HttpGet]
public IHttpActionResult GetSheetHistoryFiltered(int start, int number)
{
using (HistorySheetsController hsc = new HistorySheetsController())
{
List<HistorySheetModel> models = hsc.GetData(start, number);
return Ok(models);
}
}
[ResponseType(typeof(int))]
[Route("SheetHistoryCount"), HttpGet]
public IHttpActionResult GetSheetHistoryCount()
{
using (HistorySheetsController hsc = new HistorySheetsController())
{
return Ok(hsc.count());
}
}
}
}
@@ -18,14 +18,16 @@ using System.Linq;
namespace Thermo.Active.Controllers.WebApi
{
[RoutePrefix("api/warmers")]
public class WarmersController : ApiController
public class WarmersController : aBaseApiController // ApiController
{
#region Protected Fields
#if false
/// <summary>
/// Oggetto adapter condiviso da WebAPI
/// </summary>
protected static NcAdapter ncAdapter = new NcAdapter();
protected static NcAdapter ncAdapter = new NcAdapter();
#endif
protected static Dictionary<int, ThermoPoint> MeasurePoints = new Dictionary<int, ThermoPoint>();
@@ -589,6 +591,19 @@ namespace Thermo.Active.Controllers.WebApi
return NotFound();
}
}
/// <summary>
///Take photo Thermocam
/// </summary>
/// <param name="channelsTemp"></param>
/// <returns></returns>
[Route("takeTcamImage"), HttpPut]
[WebApiAuthorize(FunctionAccess = FUNCTIONALITY_NAMES.RECIPE_MANAGER, Action = ACTIONS.READ)]
public IHttpActionResult TakeTcamImage()
{
MessageServices.Current.Publish(TAKE_SNAPSHOT_THERMO);
return Ok();
}
#endregion Public Methods
}
@@ -0,0 +1,33 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Web.Http;
using Thermo.Active.NC;
namespace Thermo.Active.Controllers.WebApi
{
public class aBaseApiController : ApiController
{
/// <summary>
/// Oggetto adapter condiviso da WebAPI
/// </summary>
protected static NcAdapter ncAdapter = new NcAdapter();
#if false
protected override void Dispose(bool disposing)
{
if (disposing)
{
if (ncAdapter != null)
{
ncAdapter.Dispose();
}
}
base.Dispose(disposing);
}
#endif
}
}
@@ -50,7 +50,13 @@ namespace Thermo.Active.Listeners.Database
}
}
}
public static void cleanHistorySheets()
{
using (HistorySheetsController HSC = new HistorySheetsController())
{
HSC.Clean();
}
}
public static void UpdateAlarms(object alarmsObj)
{
@@ -68,6 +68,10 @@ namespace Thermo.Active.Listeners
{
SignalRListener.SendThermoChannelsIoData(a);
}));
infos.Add(MessageServices.Current.Subscribe(SEND_NEWTCAMIMAGE, (a, b) =>
{
SignalRListener.SendTCamNewImage(a);
}));
infos.Add(MessageServices.Current.Subscribe(SEND_ACTIVE_PROGRAM_DATA, (a, b) =>
{
SignalRListener.SendActiveProgramData(a);
@@ -130,6 +134,7 @@ namespace Thermo.Active.Listeners
}));
infos.Add(MessageServices.Current.Subscribe(SEND_THERMO_PROD_INFO_DATA, (a, b) =>
{
SignalRDatabaseHandler.cleanHistorySheets();
SignalRListener.SendThermoProdInfoData(a);
}));
infos.Add(MessageServices.Current.Subscribe(SEND_THERMO_PROD_CYCLE_DATA, (a, b) =>
@@ -326,6 +326,10 @@ namespace Thermo.Active.Listeners.SignalR
lastSetpointHmiInvalid = currMessage;
var context = GlobalHost.ConnectionManager.GetHubContext<NcHub>();
context.Clients.Group("ncData").setpointHmiInvalid(currMessage);
context.Clients.Group("ncData").recipeFullDataInvalidSetpoint(LastRecipeFullData);
context.Clients.Group("ncData").warmersData(LastWarmersData);
}
}
@@ -611,6 +615,13 @@ namespace Thermo.Active.Listeners.SignalR
}
}
public static void SendTCamNewImage(object newImageDate)
{
DateTime imageDate = (DateTime)newImageDate;
var context = GlobalHost.ConnectionManager.GetHubContext<NcHub>();
context.Clients.Group("ncData").newThermoCamImage(newImageDate);
}
public static void SetGatewayRebootStatus(object status)
{
string msg = status.ToString();
@@ -679,7 +690,7 @@ namespace Thermo.Active.Listeners.SignalR
// Send THERMO Recipe data
group.recipeFullData(LastRecipeFullData);
group.recipeOverData(LastRecipeOverData);
group.setpointHmiInvalid();
// Send THERMO Modules data
group.modulesData(LastModulesData);
// Send THERMO Warmers data
@@ -689,6 +700,8 @@ namespace Thermo.Active.Listeners.SignalR
group.gaugeData(LastLiveProdData);
// THERMO prod info data
group.prodInfoData(LastProdInfoData);
group.prodPanelData(LastProdPanelData);
// THERMO prod cycle data
group.prodCycleData(LastProdCycleData);
+1 -1
View File
@@ -30,4 +30,4 @@ using System.Runtime.InteropServices;
//
// You can specify all the values or you can default the Revision and Build Numbers
// by using the '*' as shown below:
[assembly: AssemblyVersion("1.1.183")]
[assembly: AssemblyVersion("1.1.192")]
+1
View File
@@ -222,6 +222,7 @@
<Compile Include="Attributes\WebApiAuthorizeAttribute.cs" />
<Compile Include="Attributes\SignalRAuthorizeAttribute.cs" />
<Compile Include="Controllers\SignalR\NcHub.cs" />
<Compile Include="Controllers\WebApi\aBaseApiController.cs" />
<Compile Include="Controllers\WebApi\ApiAlarmController.cs" />
<Compile Include="Controllers\WebApi\UnderTheHoodController.cs" />
<Compile Include="Controllers\WebApi\SchedTaskController.cs" />
+3
View File
@@ -119,6 +119,9 @@ namespace Thermo.Active
ListenersHandler.Stop();
// Close WinForm
ServerControlWindow.Stop();
// force close
Environment.Exit(0);
}
private static bool ValidateAddress(string Addr)
Binary file not shown.

After

Width:  |  Height:  |  Size: 14 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 16 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 16 KiB

@@ -2092,7 +2092,7 @@
}
.body {
height: calc(~"100%"- 64px);
height: calc(~"100%" - 64px);
overflow: hidden;
align-items: center;
justify-content: center;
@@ -3476,7 +3476,6 @@
position: absolute;
width: 100%;
height: 100%;
background: #ffffff;
top: 0;
display: block;
overflow: hidden;
@@ -3485,6 +3484,9 @@
width: 100%;
height: 100%;
cursor: -webkit-grab;
display: flex;
justify-content: center;
align-items: center;
}
.loading {
@@ -3530,6 +3532,17 @@
}
.btngroup2{
position: absolute;
bottom: 510px;
right: 0;
margin-right: 20px;
img{
box-shadow: none;
filter: grayscale(1)brightness(0)invert(1);
}
}
.btngroup {
position: absolute;
bottom: 0;
@@ -3562,11 +3575,17 @@
cursor: pointer;
color: #FFF;
z-index: 1;
display: flex;
justify-content: center;
align-items: center;
&:active{
background-image: linear-gradient(to bottom,#002680, #1756ad);
}
}
button:disabled {
background-color: #002680 !important;
;
filter: grayscale(100%);
}
+20 -4
View File
@@ -2321,7 +2321,7 @@ article .box .body {
color: #fff;
}
.modal.modal-image .body {
height: calc(100%-64px);
height: calc(100% - 64px);
overflow: hidden;
align-items: center;
justify-content: center;
@@ -3668,7 +3668,6 @@ article .box .body {
position: absolute;
width: 100%;
height: 100%;
background: #ffffff;
top: 0;
display: block;
overflow: hidden;
@@ -3677,6 +3676,9 @@ article .box .body {
width: 100%;
height: 100%;
cursor: -webkit-grab;
display: flex;
justify-content: center;
align-items: center;
}
.imageViewerZoom .loading {
position: absolute;
@@ -3715,6 +3717,16 @@ article .box .body {
margin-right: 20px;
margin-top: 20px;
}
.imageViewerZoom .btngroup2 {
position: absolute;
bottom: 510px;
right: 0;
margin-right: 20px;
}
.imageViewerZoom .btngroup2 img {
box-shadow: none;
filter: grayscale(1) brightness(0) invert(1);
}
.imageViewerZoom .btngroup {
position: absolute;
bottom: 0;
@@ -3730,8 +3742,6 @@ article .box .body {
}
.imageViewerZoom button {
font-size: 20px;
justify-content: center;
display: flex;
background-color: #ffffff;
background-image: linear-gradient(to bottom, #1756ad, #002680);
box-shadow: 0 3px 5px 0 rgba(0, 0, 0, 0.4);
@@ -3744,6 +3754,12 @@ article .box .body {
cursor: pointer;
color: #FFF;
z-index: 1;
display: flex;
justify-content: center;
align-items: center;
}
.imageViewerZoom button:active {
background-image: linear-gradient(to bottom, #002680, #1756ad);
}
.imageViewerZoom button:disabled {
background-color: #002680 !important;
+18412 -18460
View File
File diff suppressed because it is too large Load Diff
@@ -12,6 +12,7 @@ import { loginService, machineService, localizationService } from "./services";
import { prodService } from "./services/prodService";
import * as iziToast from "izitoast";
import { underTheHoodService } from "./services/underTheHoodService";
import { warmersService } from "./services/warmersService";
// import { UsersService } from "./services/usersService";
@@ -60,7 +61,6 @@ async function loadMachineConfig() {
await loginService.getUserInfo();
try {
let machine = new machineService();
let result = await machine.getAreasConfiguration();
@@ -68,12 +68,12 @@ async function loadMachineConfig() {
let mcresult = await machine.getMachineConfiguration();
machineStatusActions.setWarmersParameters(store, mcresult.additionalParameters);
await prodService.GetProdPanel();
await warmersService.GetResistances();
await underTheHoodService.getChannels();
await underTheHoodService.getChannelsConfig();
// load default language
if (!(store.state as AppModel).localization.currentLanguage) {
localizationService.changeCurrentLanguage(mcresult.defaultLanguage);
@@ -5,7 +5,7 @@
<label :class="{red: value.isScrap}" v-else>{{value.numDone}}</label>
<div class="col">
<small>{{'history-item_warmup' | localize("tempo riscaldo")}}</small>
<span>{{Math.floor(value.timeWarm / 60) | round(0)}}'{{value.timeWarm % 60 | round(0)}}''</span>
<span>{{value.timeWarm | round(0)}}''</span>
</div>
<div class="col">
<small>{{'history-item_vacuum' | localize("vuoto")}}</small>
@@ -29,7 +29,7 @@
</div>
<div class="col">
<small>{{'history_item_venttime' | localize("tempo ventilazione")}}</small>
<span>{{value.timeVent / 60 | round(0)}}'{{value.timeVent % 60 | round(0)}}''</span>
<span>{{value.timeVent | round(0)}}''</span>
</div>
<div class="col">
<small>{{'history_item_cycletimegross' | localize("tempo ciclo lordo")}}</small>
@@ -53,7 +53,7 @@
<div class="row">
<div class="col">
<small>{{'history_item_vacuumtime' | localize("tempo vuoto")}}</small>
<span>{{Math.floor(value.timeVacuum / 60) | round(0)}}'{{value.timeVacuum % 60 | round(0)}}''</span>
<span>{{value.timeVacuum | round(0)}}''</span>
</div>
<div class="col">
<small>{{'history_item_mouldenergyin' | localize("energia utilizzata in")}}</small>
@@ -9,7 +9,6 @@ export default class stats extends Vue {
value: { [id: number]: number };
get Values(): number[] {
console.log(this.value);
var r: number[] = [];
if (this.value)
for (const i in this.value) {
@@ -10,18 +10,6 @@
<line :x1="0" :x2="width" :y1="height*2/3" :y2="height*2/3" stroke="#353535" stroke-width="1" />
<line :x1="0" :x2="width" :y1="height" :y2="height" stroke="#353535" stroke-width="1" />
</g>
<!--<g chart="chart-axis">
<line
v-for="(i,idx) in Values"
:key="idx"
:x1="idx * (width / 19)"
:x2="idx * (width / 19)"
:y1="0"
:y2="height"
stroke="#35353550"
stroke-width="1"
/>
</g>-->
<g>
<polygon :points="calcPointFill" style="fill:#1791ff;stroke-width:0" fill-opacity="0.3" />
<path fill="none" :d="pathData" v-if="pathData" stroke="#1791ff" stroke-width="4" />
@@ -118,8 +118,6 @@ export default class Dashboard extends Vue {
this.itemsMap.set(i.numDone, i);
}
this.items = Array.from(this.itemsMap.values()).sort((a, b) => b.numDone - a.numDone);
console.log(this.items);
this.loading = false;
}
@@ -132,8 +130,6 @@ export default class Dashboard extends Vue {
}
async mounted() {
prodService.GetProdPanel();
let $this = this;
setInterval(() => {
$this.now = moment();
@@ -204,13 +200,33 @@ export default class Dashboard extends Vue {
}
incrementPyr() {
this.recipe.pyrometer_pyrometer_setpoint.setpointHMI++;
this.recipe.pyrometer_pyrometer_setpoint.setpointHMI++;
this.recipe.pyrometer_upperthermoregulator_start_adjustment.setpointHMI++;
this.recipe.pyrometer_upperthermoregulator_end_adjustment.setpointHMI++;
this.recipe.pyrometer_lowerthermoregulator_start_adjustment.setpointHMI++;
this.recipe.pyrometer_lowerthermoregulator_end_adjustment.setpointHMI++;
this.debouncedRecipeSave();
}
decrementPyr() {
this.recipe.pyrometer_pyrometer_setpoint.setpointHMI--;
this.recipe.pyrometer_pyrometer_setpoint.setpointHMI--;
this.recipe.pyrometer_upperthermoregulator_start_adjustment.setpointHMI--;
this.recipe.pyrometer_upperthermoregulator_end_adjustment.setpointHMI--;
this.recipe.pyrometer_lowerthermoregulator_start_adjustment.setpointHMI--;
this.recipe.pyrometer_lowerthermoregulator_end_adjustment.setpointHMI--;
this.debouncedRecipeSave();
}
togglePyr() {
if(this.recipe.pyrometer_pyrometer_enabled.setpointHMI == 1)
this.recipe.pyrometer_pyrometer_enabled.setpointHMI = 0;
else
this.recipe.pyrometer_pyrometer_enabled.setpointHMI = 1;
this.debouncedRecipeSave();
}
get pyrOn(){
return this.recipe.pyrometer_pyrometer_enabled.setpointHMI == 1;
}
debouncedRecipeSave = debounce(this.savePyr, 1000);
public async savePyr(){
@@ -229,7 +245,11 @@ export default class Dashboard extends Vue {
get payload() {
return {
pyrometer_pyrometer_enabled: this.recipe.pyrometer_pyrometer_enabled,
pyrometer_pyrometer_setpoint: this.recipe.pyrometer_pyrometer_setpoint
pyrometer_pyrometer_setpoint: this.recipe.pyrometer_pyrometer_setpoint,
pyrometer_upperthermoregulator_start_adjustment: this.recipe.pyrometer_upperthermoregulator_start_adjustment,
pyrometer_upperthermoregulator_end_adjustment: this.recipe.pyrometer_upperthermoregulator_end_adjustment,
pyrometer_lowerthermoregulator_start_adjustment: this.recipe.pyrometer_lowerthermoregulator_start_adjustment,
pyrometer_lowerthermoregulator_end_adjustment: this.recipe.pyrometer_lowerthermoregulator_end_adjustment,
}
}
@@ -118,9 +118,11 @@
<button @click="decrementPyr()" :disabled="!recipe.pyrometer_pyrometer_setpoint.status.enabled" >
<i class="fa fa-minus"></i>
</button>
<div :class="{'notenabled': recipe.pyrometer_pyrometer_enabled.setpointHMI == 0}">
<div :class="{'notenabled': recipe.pyrometer_pyrometer_enabled.setpointHMI == 0}" @click="togglePyr">
<small>{{'dashboard-setpoint' | localize('set point')}}</small>
<span :class="{'strike': recipe.pyrometer_pyrometer_enabled.setpointHMI == 0}">{{recipe.pyrometer_pyrometer_setpoint.setpointHMI}}{{recipe.pyrometer_pyrometer_setpoint.unitMeasure}}</span>
<div v-if="pyrOn">ON</div>
<div v-else>OFF</div>
</div>
<button @click="incrementPyr()" :disabled="!recipe.pyrometer_pyrometer_setpoint.status.enabled" >
<i class="fa fa-plus"></i>
@@ -42,8 +42,8 @@ export default class SVGCaricatore extends Vue{
minoreuguale:string="<=";
getPositionSheet(id,col){
var vent = ((this.larghTelaioSVG + (this.dimVentose*2)) / (this.numVentose +1));
var posX = (id*vent ) - (this.dimVentose*2);
var vent = (this.larghTelaioSVG - (this.dimVentose*2)) / (this.numVentose -1);
var posX = (id-1)*vent;
if(col == 1)
return "translate(-630 -147) translate(50 25) translate(580 122) translate(0 70) translate(0 0) translate("+ posX + ")";
else if(col == 2)
@@ -1,6 +1,6 @@
<template>
<div class="svg-area">
<svg xmlns="http://www.w3.org/2000/svg" width="1057" height="707" viewBox="0 0 1100 707">
<svg xmlns="http://www.w3.org/2000/svg" width="1057" height="707" viewBox="-50 0 1150 707">
<g fill="none" fill-rule="evenodd">
<g>
<g>
@@ -122,10 +122,6 @@ export default class ShowCicloInfo extends Vue {
if (el.status.visible && el.status.enabled)
if (el.setpointHMI != el.setpointPLC) result = true;
}
for (const key in store.state.warmers.channels) {
const el = store.state.warmers.channels[key];
if (el.setpointHMI != el.setpointPLC) result = true;
}
return result;
}
@@ -20,6 +20,12 @@
position: relative;
cursor: pointer;
}
.bitSelect .form.error {
outline: 2px #d0021b auto !important;
}
.bitSelect .form.disabled {
background-color: rgba(0, 0, 0, 0.15);
}
.bitSelect .form i {
position: absolute;
right: 4px;
@@ -40,6 +46,18 @@
overflow: hidden;
height: auto !important;
width: 500px !important;
border-top: 1px solid #979797;
border-left: 1px solid #979797;
}
.bitSelect > section.bitsections .selall {
grid-column-start: 1;
grid-column-end: 3;
display: flex;
justify-content: flex-end;
align-items: center;
margin: 24px 0px 0 0;
height: 64px;
border-top: 2px solid #bbbcbc;
}
.bitSelect > section.bitsections > article {
height: 70px !important;
@@ -47,7 +65,8 @@
grid-template-columns: 68px 1fr;
align-items: center;
justify-items: center;
border: 1px solid #979797;
border-bottom: 1px solid #979797;
border-right: 1px solid #979797;
}
.bitSelect > section.bitsections > article label {
width: 100%;
@@ -19,6 +19,16 @@
padding-right: 25px;
position: relative;
cursor: pointer;
&.error{
outline: 2px #d0021b auto !important;
}
&.disabled{
background-color: rgba(0, 0, 0, 0.15);
}
i {
position: absolute;
right: 4px;
@@ -27,7 +37,7 @@
}
}
> section.bitsections {
> section.bitsections {
position: absolute !important;
top: 48px;
right: 0;
@@ -42,13 +52,28 @@
height: auto !important;
width: 500px !important;
border-top: 1px solid #979797;
border-left: 1px solid #979797;
.selall{
grid-column-start:1;
grid-column-end:3;
display: flex;
justify-content: flex-end;
align-items: center;
margin: 24px 0px 0 0;
height: 64px;
border-top: 2px solid #bbbcbc;
}
> article {
height: 70px !important;
display: grid !important;
grid-template-columns: 68px 1fr;
align-items: center;
justify-items: center;
border: 1px solid #979797;
border-bottom: 1px solid #979797;
border-right: 1px solid #979797;
label {
width: 100%;
@@ -23,6 +23,13 @@ export default class bitSelect extends Vue {
this.value.setpointHMI = v;
}
openclose(){
if(!this.value || !this.value.status || !this.value.status.enabled)
return
this.opened = !this.opened
}
get currentValue() {
let result = []
for (let index = 0; index < this.bitSize; index++) {
@@ -66,4 +73,20 @@ export default class bitSelect extends Vue {
return this.bit_test(this.value.range.max,bit-1);
}
setAll(){
this.Value = this.value.range.max;
for (let i = 0; i < this.bitSize; i++) {
Vue.set(this.bits, i, this.bit_test(this.Value, i))
}
}
clearAll(){
this.Value = 0;
for (let i = 0; i < this.bitSize; i++) {
Vue.set(this.bits, i, this.bit_test(this.Value, i))
}
}
}
@@ -2,7 +2,7 @@
<div class="bitSelect">
<div
class="form"
@click="opened = !opened"
@click="openclose"
:class="{'error': value && value.status && value.status.hasError, 'disabled': value && value.status && !value.status.enabled}"
>
{{currentValue}}
@@ -23,7 +23,11 @@
</div>
<label :for="`cb-${b}`">{{`${key}_${b}` | localize((b).toString())}}</label>
</article>
</template>
</template>
<div class="selall">
<button class="btn" @click="clearAll">{{'bitselect_select_none' | localize('Nessuno')}}</button>
<button class="btn btn-success" @click="setAll">{{'bitselect_select_all' | localize('Tutti')}}</button>
</div>
</section>
</div>
</template>
@@ -68,17 +68,26 @@
.modal.prophetimages section .image-selector .timeseries {
width: 100%;
position: relative;
display: flex;
flex-flow: row;
align-items: center;
justify-content: space-between;
}
.modal.prophetimages section .image-selector .timeseries time {
color: #002680;
font-size: 18px;
font-weight: 500;
width: 200px;
position: absolute;
display: flex;
flex-flow: column;
align-items: center;
}
.modal.prophetimages section .image-selector .timeseries time:last-child {
align-items: flex-end;
}
.modal.prophetimages section .image-selector .timeseries time:first-child {
align-items: flex-start;
}
.modal.prophetimages section .image-selector .selector {
color: #002680;
font-size: 18px;
@@ -101,7 +110,7 @@
}
.modal.prophetimages section .color-bar .color-line {
height: 100%;
background-image: linear-gradient(to bottom, #fff, #ffdf00 16%, #e40000 37%, #ab00a5 62%, #000ca4 86%, #000000);
background-image: linear-gradient(to bottom, #ffffff, #ffffcc 16%, #ff9900 48%, #ff0066 64%, #3300ff 80%, #000033);
}
.modal.prophetimages section .color-bar .legend {
display: flex;
@@ -69,17 +69,26 @@
.timeseries {
width: 100%;
position: relative;
display: flex;
flex-flow: row;
align-items: center;
justify-content: space-between;
time {
color: #002680;
font-size: 18px;
font-weight: 500;
width: 200px;
position: absolute;
display: flex;
flex-flow: column;
align-items: center;
}
time:last-child{
align-items:flex-end;
}
time:first-child{
align-items:flex-start;
}
}
.selector {
@@ -109,12 +118,12 @@
height: 100%;
background-image: linear-gradient(
to bottom,
#fff,
#ffdf00 16%,
#e40000 37%,
#ab00a5 62%,
#000ca4 86%,
#000000
rgba(255,255,255,1),
rgba(255,255,204,1) 16%,
rgba(255,153,0,1) 48%,
rgba(255,0,102,1) 64%,
rgba(51,0,255,1) 80%,
rgba(0,0,51,1)
);
}
@@ -32,6 +32,7 @@ export default class ThermoModal extends Vue {
selectedImage: number = 0;
serverPath = "/thermoprophet/colored";
items: Prod.IProd[] = [];
get images() {
return this.items.map(i => i.thermoImage)
}
@@ -48,6 +49,7 @@ export default class ThermoModal extends Vue {
this.TCamData = await warmersService.GetTCamData();
await warmersService.ResetMeasurePoints();
console.log(this.lastItem);
let min = Math.min(this.lastItem.numDone);
this.items.push(...await prodService.History(min - 1, min - 1))
}
@@ -63,6 +65,10 @@ export default class ThermoModal extends Vue {
this.reloadMeasuresDelayed(this.images[this.selectedImage], this.measurePoints);
}
getImageCycle(Sel){
return this.items[Sel];
}
@Watch("selectedImage")
reloadMeasuresDelayed = debounce(async (image, points) => {
let result = await warmersService.GetMeasurePoints(image);
@@ -6,10 +6,16 @@
<div class="imagecontainer">
<img
:src="`${serverPath}/${images[parseInt(selectedImage)]}.jpg`"
v-if="images.length && images[selectedImage]!='UNDEFINED'"
@click="imageclick"
v-if="images.length"
ref="mainimage"
/>
/>
<img
src="assets\icons\png\NOCamera.png"
v-if="images.length && images[selectedImage]=='UNDEFINED'"
ref="mainimage"
/>
<span>{{'thermo-long-tap-info' | localize("Long tap on image to add temperature inspectors")}}</span>
<div
@@ -29,14 +35,21 @@
</div>
<div class="image-selector">
<div class="timeseries">
<!-- <time>{{'first-image' | localize("First image")}}</time>
<time>{{'last-image' | localize("Last image")}}</time>-->
<time>{{'last-image' | localize("Last image")}}</time>
<time class="center">&nbsp;</time>
<time>{{'first-image' | localize("First image")}}</time>
</div>
<img
:src="`${serverPath}/${images[parseInt(selectedImage)]}.jpg`"
v-if="showPreview"
v-if="showPreview && images[selectedImage]!='UNDEFINED'"
class="selector"
:style="`left:${(parseInt(selectedImage) / (images.length-1)) * 858}px`"
/>
<img
src="assets\icons\png\NOCamera.png"
v-if="showPreview && images[selectedImage]=='UNDEFINED'"
class="selector"
:style="`left:${(parseInt(selectedImage) / (images.length-1)) * 858}px; background-color:#ffffff;`"
/>
<input
v-if="images.length"
@@ -50,8 +63,9 @@
<div class="selectorarea">
<span
class="selector"
v-if="getImageCycle(selectedImage)"
:style="`left:${(parseInt(selectedImage) / (images.length-1)) * 858}px`"
>{{'thermo-cycle' | localize("Cycle")}} {{selectedImage}}</span>
>{{'thermo-cycle' | localize("Cycle")}} {{getImageCycle(selectedImage).numDone}}</span>
</div>
</div>
</modal>
@@ -0,0 +1,70 @@
.warmers {
display: grid !important;
grid-template-columns: 1fr 70px;
margin-right: -14px;
}
.warmers .right-controls {
display: flex;
flex-flow: column nowrap;
align-items: center;
justify-content: space-between;
}
.warmers .right-controls .tm-controls {
display: flex;
flex-flow: column;
align-items: center;
justify-content: space-between;
height: 420px;
}
.warmers .right-controls .tm-controls input[type="range"][orient="vertical"] {
writing-mode: bt-lr;
/* IE */
-webkit-appearance: slider-vertical;
/* WebKit */
width: 6px;
height: 150px;
border: none !important;
box-shadow: inset 0 1px 3px 0 rgba(0, 0, 0, 0.5);
border-radius: 10px;
}
.warmers .right-controls .tm-controls input[type="range"][orient="vertical"]::-webkit-slider-thumb {
min-width: 30px;
min-height: 30px;
border: none;
background: none !important;
appearance: none;
}
.warmers .right-controls .tm-controls input[type="range"]::-webkit-slider-thumb {
background-color: linear-gradient(to bottom, #1756ad, #002e6e 97%) !important;
}
.warmers .right-controls .um-buttons {
background-color: #dddddd;
height: 130px;
width: 40px;
border-radius: 20px;
box-shadow: inset 0 1px 3px 0 rgba(0, 0, 0, 0.5);
display: flex;
flex-flow: column nowrap;
justify-content: space-around;
align-items: center;
}
.warmers .right-controls .um-buttons button {
width: 34px;
height: 34px;
border-radius: 50px;
border: none;
text-align: center;
line-height: 34px;
font-size: 18px;
font-weight: bold;
color: #fff;
box-shadow: inset 0 2px 2px 0 rgba(0, 0, 0, 0.19);
background-color: rgba(187, 188, 188, 0.5);
}
.warmers .right-controls .um-buttons button.selected {
box-shadow: 0 2px 2px 0 rgba(0, 0, 0, 0.5);
background-image: linear-gradient(to bottom, #1756ad, #002e6e 97%);
}
.warmers .right-controls .buttons button {
margin: 8px;
}
@@ -13,13 +13,13 @@
flex-flow: column;
align-items: center;
justify-content: space-between;
height: 350px;
height: 420px;
input[type="range"][orient="vertical"] {
writing-mode: bt-lr; /* IE */
-webkit-appearance: slider-vertical; /* WebKit */
width: 6px;
height: 250px;
height: 150px;
border: none !important;
box-shadow: inset 0 1px 3px 0 rgba(0, 0, 0, 0.5);
border-radius: 10px;
@@ -8,11 +8,14 @@ import { warmersService } from "@/services/warmersService";
import { awaiter } from '@/_base';
import termoModal from "./thermoProphet-modal.vue";
import { ModalHelper } from '@/components/modals';
import moment from "moment";
import { messageService } from "src/_base";
import ModalImage from "@/modules/base-components/modal-image.vue";
@Component({
name: "thermocamera", components: {
warmers
warmers,ModalImage
}
})
export default class Thermocamera extends Vue {
@@ -29,19 +32,28 @@ export default class Thermocamera extends Vue {
thermoImageOpacity: number = 0;
resistanceMode = 0;
timeoutLastTakenImage = 0;
timeCamDiff = " ";
tcamBTNStatus:{
enabled: boolean,
visible: boolean
} = {enabled : false, visible: true};
TCamData: {
imageSize: { x: number, y: number },
rangeTemperature: { max: number, min: number },
thermoCamConnected: boolean,
thermoOptionActive: boolean,
lastTakenImage: Date,
} = null;
@Watch("warmers", { deep: true })
async ChangedTemps() {
this.btnModeEnabled = false;
this.tcamBTNStatus.enabled = false;
for (const ch of store.state.warmers.channels) {
if (ch.tCamTempSet > 0) {
this.btnModeEnabled = true;
if (ch.tCamTempSet > 0 && ch.tCamActive) {
this.tcamBTNStatus.enabled = true;
break;
}
}
@@ -53,6 +65,13 @@ export default class Thermocamera extends Vue {
async mounted() {
this.ChangedTemps();
this.TCamData = await warmersService.GetTCamData();
messageService.subscribeToChannel("new-thermocam-image", (args)=>{
if(this.TCamData){
this.TCamData.lastTakenImage = args[0];
ModalHelper.modalImage.content = this.thermocameraOriginalUrl;
}
});
}
get selectedChannels(): Warmers.IChannel[] {
@@ -75,6 +94,50 @@ export default class Thermocamera extends Vue {
// return (store.state.warmers.tCamStatus.thermoCamMode);
// }
get thermocameraImageUrl(){
if(!this.TCamData || moment(this.TCamData.lastTakenImage).year() <= 2000)
return "/thermoprophet/colored/_last.jpg?lastmod=NOTAVAILABLE";
return "/thermoprophet/colored/_last.jpg?lastmod=" + this.TCamData.lastTakenImage;
}
get thermocameraOriginalUrl(){
if(!this.TCamData || moment(this.TCamData.lastTakenImage).year() <= 2000)
return "/thermoprophet/original/_last.jpg?lastmod=NOTAVAILABLE";
return "/thermoprophet/original/_last.jpg?lastmod=" + this.TCamData.lastTakenImage;
}
get thermocameraImageOk(): boolean {
clearInterval(this.timeoutLastTakenImage);
this.timeCamDiff = " "
if(!this.TCamData)
return false;
if(moment(this.TCamData.lastTakenImage).year() > 2000)
{
this.lastTakenImageFuncion();
this.timeoutLastTakenImage = setInterval(this.lastTakenImageFuncion,10000);
return true;
}
return false;
}
lastTakenImageFuncion(){
var today = moment(new Date());
var end = moment(this.TCamData.lastTakenImage);
var diff = (moment.duration(today.diff(end)) as any)._data;
var seconds = diff.seconds;
var minutes = diff.minutes;
var hours = diff.hours;
if(hours >0)
this.timeCamDiff = hours + "h " + minutes + "m ";
else if(minutes >0)
this.timeCamDiff = minutes + "m " + seconds + "s ";
else
this.timeCamDiff = seconds + "s";
}
get thermocameraModeBTN(): boolean {
return (store.state.warmers.tCamStatus.thermoCamOnOff);
}
@@ -177,4 +240,19 @@ export default class Thermocamera extends Vue {
async openThermoModal() {
ModalHelper.ShowModal(termoModal, "modal2");
}
async openImageModal() {
if(this.TCamData){
ModalHelper.modalImage.title = moment(this.TCamData.lastTakenImage).format("L") + " - " + moment(this.TCamData.lastTakenImage).format("LTS");
}
ModalHelper.modalImage.content = this.thermocameraOriginalUrl;
ModalHelper.ShowModal(ModalImage, "modal2");
}
async forceTakeImage() {
warmersService.TakeNewPhoto();
}
}
@@ -79,7 +79,7 @@
<div class="input-area grid left">
<label>{{'warmers_thermoprophet_Enabled' | localize('Thermoprophet')}}</label>
<toggle-button v-model="thermocameraModeBTN"></toggle-button>
<toggle-button v-model="thermocameraModeBTN" :status="tcamBTNStatus"></toggle-button>
</div>
<!-- <div class="input-area left grid">
@@ -111,8 +111,8 @@
@methodChanged="m => selectionMethod = m"
:recipe="recipe"
:resistanceMode="resistanceMode"
thermoImage="/thermoprophet/colored/_last.jpg"
:thermoImageVisible="thermocameraModeBTN"
:thermoImage="thermocameraImageUrl"
:thermoImageVisible="true"
:thermoImageOpacity="thermoImageOpacity"
:isThermoProphet="true"
></warmers>
@@ -125,11 +125,18 @@
</div>
<div class="tm-controls">
<button class="btn btn-info square" @click="openThermoModal()">
<button class="btn btn-info square" @click="forceTakeImage()" :disabled="this.thermocameraModeBTN">
<img src="/assets/icons/png/takesnap.png" />
</button>
<button class="btn btn-info square" @click="openImageModal()">
<img src="/assets/icons/png/ico-bt-selez-image.png" />
</button>
<button class="btn btn-info square" @click="openThermoModal()">
<img src="/assets/icons/png/history.png" />
</button>
<span>{{timeCamDiff}}</span>
<input
:disabled="!thermocameraModeBTN"
:disabled="!thermocameraImageOk"
type="range"
orient="vertical"
v-model="thermoImageOpacity"
@@ -141,7 +148,7 @@
</div>
<div class="buttons">
<button class="btn btn-info square icon" @click="zoomIn()">
<button class="btn btn-info square icon" @click="zoomIn()" >
<i class="fa fa-search-plus"></i>
</button>
<button class="btn btn-info square icon" @click="zoomReset()">
@@ -90,7 +90,6 @@ export default class Warmers extends Vue {
// Ottengo le resistenze per ogni riga
resistancesPerRow(row: number) {
console.log(row,this.resistances.filter(i => i.row == row))
return this.resistances.filter(i => i.row == row);
}
@@ -70,6 +70,9 @@ export default class VuotoPrincipale extends Vue {
if(this.recipe.vacuum_main_2_chart_setpointx.setpointHMI <= 0 && this.recipe.vacuum_main_3_chart_setpointx.setpointHMI <= 0){
this.recipe.vacuum_main_1_chart_setpointx.setpointHMI = this.recipe.vacuum_main_max_time.setpointHMI;
this.recipe.vacuum_main_2_chart_setpointx.setpointHMI = 0;
this.recipe.vacuum_main_3_chart_setpointx.setpointHMI = 0;
}
else if (this.recipe.vacuum_main_3_chart_setpointx.setpointHMI > 0){
diff = this.recipe.vacuum_main_max_time.setpointHMI -
@@ -86,6 +89,7 @@ export default class VuotoPrincipale extends Vue {
this.recipe.vacuum_main_3_chart_setpointx.setpointHMI;
this.recipe.vacuum_main_2_chart_setpointx.setpointHMI = diff;
this.recipe.vacuum_main_3_chart_setpointx.setpointHMI = 0;
}
}
else{
@@ -103,6 +107,7 @@ export default class VuotoPrincipale extends Vue {
this.recipe.vacuum_main_3_chart_setpointx.setpointHMI;
this.recipe.vacuum_main_2_chart_setpointx.setpointHMI = diff;
this.recipe.vacuum_main_3_chart_setpointx.setpointHMI = 0;
}
}
@@ -130,6 +135,7 @@ export default class VuotoPrincipale extends Vue {
{
if(this.recipe.vacuum_main_3_chart_setpointx.setpointHMI <= 0){
this.recipe.vacuum_main_2_chart_setpointx.setpointHMI = this.recipe.vacuum_main_max_time.setpointHMI - this.recipe.vacuum_main_1_chart_setpointx.setpointHMI;
this.recipe.vacuum_main_3_chart_setpointx.setpointHMI = 0;
}
else{
diff = this.recipe.vacuum_main_max_time.setpointHMI -
@@ -27,8 +27,8 @@ export default class outputRow extends Vue {
async force(value: number) {
if(!this.item.isForced && (this.item.forcedValue === undefined || value != this.item.forcedValue))
{
ModalHelper.AskConfirm( this.$options.filters.localize("Richiesta di conferma","modal_confirm_title"),
this.$options.filters.localize("Confirm?","softkey_confirm"),
ModalHelper.AskConfirm( this.$options.filters.localize("modal_confirm_title", "Richiesta di conferma"),
this.$options.filters.localize("softkey_confirm", "Confirm?"),
async() => {
await underTheHoodService.forceChannel(this.group, this.item, value);
}, null, "modal");
@@ -2,8 +2,37 @@ import { Component, Vue } from "vue-property-decorator";
import Header from "../../../header/my-header.vue";
import MenuSx from "../../../menu-sx/menu-sx.vue";
import LogMisurazioniTable from "../../../LogMisurazioni/components/tables/log-misurazioni-table/log-misurazioni-table.vue";
import { awaiter, messageService } from "@/_base";
import { CustomPagination } from "@/components/pagination";
import { Watch } from "vue-property-decorator";
import { underTheHoodService } from "@/services/underTheHoodService";
@Component({
components: { Header, MenuSx, LogMisurazioniTable }
components: { Header, MenuSx, LogMisurazioniTable,CustomPagination }
})
export default class LogMisurazioni extends Vue {}
export default class LogMisurazioni extends Vue {
currentPage: number = 0;
itemsPerPage: number = 10;
totalPages: number = 1;
rowData = [];
async mounted(){
this.reload();
}
@Watch("currentPage", { deep: true })
async getLogs(){
var from = ((this.currentPage) * 10);
this.rowData = (await awaiter(underTheHoodService.GetHistorySheetsFitered(from,this.itemsPerPage)));
}
async reload(){
this.currentPage = 0;
this.totalPages = await awaiter(underTheHoodService.GetHistorySheetsCount()) / this.itemsPerPage;
this.getLogs();
}
}
@@ -1,6 +1,18 @@
<template>
<div class="column-page-one-column">
<LogMisurazioniTable></LogMisurazioniTable>
<LogMisurazioniTable :rowData="rowData"></LogMisurazioniTable>
<div class="menu">
<div class="load">
<custom-pagination
v-model="currentPage"
:items-per-page="itemsPerPage"
:total-pages="totalPages"
></custom-pagination>
</div>
<div class="toReload">
<button class="btn" @click="reload()"><i class="fa fa-refresh"></i></button>
</div>
</div>
</div>
</template>
<style lang="less">
@@ -0,0 +1,28 @@
.main-container th,
.main-container td {
padding: 0 5px;
}
.main-container th.left,
.main-container td.left {
text-align: end;
}
.main-container th.lastre-date,
.main-container td.lastre-date {
width: 20%;
}
.main-container th.lastre-recipe,
.main-container td.lastre-recipe {
width: 20%;
}
.main-container th.lastre-numpezzo,
.main-container td.lastre-numpezzo {
width: 10%;
}
.main-container th.lastre-type,
.main-container td.lastre-type {
width: 20%;
}
.main-container th.lastre-value,
.main-container td.lastre-value {
width: 30%;
}
@@ -3,21 +3,24 @@
.main-container {
th,
td {
&.misurazioni-value {
width: 322px;
max-width: 322px;
padding: 0 5px;
&.left{
text-align: end;
}
&.misurazioni-recipe {
width: 539px;
max-width: 539px;
&.lastre-date {
width: 20%;
}
&.misurazioni-date {
width: 313px;
max-width: 313px;
&.lastre-recipe {
width: 20%;
}
&.misurazioni-type {
width: 187px;
max-width: 187px;
&.lastre-numpezzo {
width: 10%;
}
&.lastre-type {
width: 20%;
}
&.lastre-value {
width: 30%;
}
}
}
@@ -1,83 +1,33 @@
import { Component, Vue } from "vue-property-decorator";
import { Prop } from "vue-property-decorator";
import moment from "moment";
@Component({})
export default class LogMisurazioniTable extends Vue {
rowData = [];
@Prop({ default: []})
rowData:any;
mounted() {
this.rowData = [
{
date: "2020-09-16 00:23:20 UTC",
recipe: "Recipe name [30]",
type: "Lenght",
value: "568.08 mm [589.92 mm - 21.84 mm]"
},
{
date: "2020-09-16 00:23:20 UTC",
recipe: "Recipe name [30]",
type: "Lenght",
value: "568.08 mm [589.92 mm - 21.84 mm]"
},
{
date: "2020-09-16 00:23:20 UTC",
recipe: "Recipe name [30]",
type: "Lenght",
value: "568.08 mm [589.92 mm - 21.84 mm]"
},
{
date: "2020-09-16 00:23:20 UTC",
recipe: "Recipe name [30]",
type: "Lenght",
value: "568.08 mm [589.92 mm - 21.84 mm]"
},
{
date: "2020-09-16 00:23:20 UTC",
recipe: "Recipe name [30]",
type: "Lenght",
value: "568.08 mm [589.92 mm - 21.84 mm]"
},
{
date: "2020-09-16 00:23:20 UTC",
recipe: "Recipe name [30]",
type: "Lenght",
value: "568.08 mm [589.92 mm - 21.84 mm]"
},
{
date: "2020-09-16 00:23:20 UTC",
recipe: "Recipe name [30]",
type: "Lenght",
value: "568.08 mm [589.92 mm - 21.84 mm]"
},
{
date: "2020-09-16 00:23:20 UTC",
recipe: "Recipe name [30]",
type: "Lenght",
value: "568.08 mm [589.92 mm - 21.84 mm]"
},
{
date: "2020-09-16 00:23:20 UTC",
recipe: "Recipe name [30]",
type: "Lenght",
value: "568.08 mm [589.92 mm - 21.84 mm]"
},
{
date: "2020-09-16 00:23:20 UTC",
recipe: "Recipe name [30]",
type: "Lenght",
value: "568.08 mm [589.92 mm - 21.84 mm]"
},
{
date: "2020-09-16 00:23:20 UTC",
recipe: "Recipe name [30]",
type: "Lenght",
value: "568.08 mm [589.92 mm - 21.84 mm]"
},
{
date: "2020-09-16 00:23:20 UTC",
recipe: "Recipe name [30]",
type: "Lenght",
value: "568.08 mm [589.92 mm - 21.84 mm]"
}
];
}
convertDate(date) {
return moment(date).format('L');
}
convertDateToTime(date) {
return moment(date).format('LTS');
}
convertType(item){
if (!item || item == 0)
return "ND"
else if (item == 1)
return "PALLET HEIGHT"
else if (item == 2)
return "SHEET THICKNESS"
else if (item == 2)
return "SHEET LENGTH"
else
return "ND"
}
}
@@ -3,40 +3,28 @@
<table>
<thead>
<tr>
<th class="misurazioni-date">Date</th>
<th class="misurazioni-recipe">Recipe</th>
<th class="misurazioni-type">Type</th>
<th class="misurazioni-value">Value</th>
<th class="lastre-date ">{{'underthehood_label_date' | localize("Date")}}</th>
<th class="lastre-recipe">{{'underthehood_label_recipe' | localize("Ricetta")}}</th>
<th class="lastre-numpezzo left">{{'underthehood_label_numpiece' | localize("N. Pezzo")}}</th>
<th class="lastre-type left">{{'underthehood_label_type' | localize("Type")}}</th>
<th class="lastre-value left">{{'underthehood_label_value' | localize("Value")}}</th>
</tr>
</thead>
<tbody class="autocolor">
<tr v-for="(item, i) of rowData" :key="i" class="tr-inner">
<td>
<span>
{{ item.date }}
</span>
</td>
<td>
<span>
{{ item.recipe }}
</span>
</td>
<td>
<span>
{{ item.type }}
</span>
</td>
<td>
<span>
{{ item.value }}
</span>
</td>
</tr>
<template v-for="(item, idx) in rowData">
<tr :key="`c-${idx}`">
<td>{{convertDate(item.dtEvent)}} - {{convertDateToTime(item.dtEvent)}}</td>
<td>{{item.recipeName}}</td>
<td class="left">{{item.numDone}}</td>
<td class="left">{{convertType(item.typeVal)}}</td>
<td class="left">{{item.firstVal | round(1)}} [{{item.secondVal | round(1)}}, {{item.thirdVal | round(1)}}]</td>
</tr>
</template>
</tbody>
</table>
</table>
</div>
</template>
<style lang="less">
@import "log-misurazioni-table.less";
</style>
<script lang="ts" src="./log-misurazioni-table.ts"></script>
<script lang="ts" src="./log-misurazioni-table.ts"></script>
@@ -14,7 +14,6 @@ export default class RiscaldiTable extends Vue {
}
getChannelInfo(id) {
console.log(store.state.warmers.channels.filter(i => i.idChannel == 5)[0]);
return store.state.warmers.channels.filter(i => i.idChannel == id)[0];
}
@@ -10,11 +10,11 @@
@click="go('log-ciclo-automatico')"
:class="{white: this.value == 'log-ciclo-automatico'}"
>{{'underthehood_label_loga' | localize("Log ciclo automatico")}}</div>
<!-- <div
<div
class="rettangle"
@click="go('log-misurazioni')"
:class="{white: this.value == 'log-misurazioni'}"
>{{'underthehood_label_logm' | localize("Log misurazioni")}}</div>-->
>{{'underthehood_label_logm' | localize("Log misurazioni")}}</div>
<div
class="rettangle"
@click="go('assi')"
@@ -49,7 +49,8 @@ export class ModalHelper {
};
public static modalImage = {
content: null,
title: null
title: null,
lastPhoto:null
};
public static maintenanceModal = {
currentMaintenance: null,
-6
View File
@@ -24,12 +24,6 @@ import "./app.business-logic";
import "./app.modules";
import { messageService } from "src/_base";
import { warmersService } from "./services/warmersService";
warmersService.GetChannels();
warmersService.GetResistances();
import { prodService } from "./services/prodService";
prodService.GetProd();
const App = () =>
import("./App.vue");
@@ -3,6 +3,7 @@ import { Factory, messageService } from "../../_base";
import ZoomImage from './zoom-image.vue'
import Vue from "vue";
import Component from "vue-class-component";
import moment from "moment";
@Component({
components:{
@@ -13,19 +14,24 @@ import Component from "vue-class-component";
export default class ModalImage extends Vue {
content: string = "";
title: string = "";
content: string = "";
title: string = "";
mounted() {
this.content = ModalHelper.modalImage.content;
this.title = ModalHelper.modalImage.title;
messageService.subscribeToChannel("new-thermocam-image", (args)=>{
this.content = "/thermoprophet/original/_last.jpg?lastmod=" + args[0];
this.title = moment(args[0]).format("L") + " - " + moment(args[0]).format("LTS");
});
}
mounted() {
this.content = ModalHelper.modalImage.content;
this.title = ModalHelper.modalImage.title;
}
beforeMount() {
messageService.subscribeToChannel("esc_pressed", args => {
this.close();
});
beforeMount() {
messageService.subscribeToChannel("esc_pressed", args => {
this.close();
});
}
beforeDestroy() {
@@ -34,7 +40,7 @@ export default class ModalImage extends Vue {
close() {
messageService.deleteChannel("esc_pressed");
ModalHelper.HideModal();
ModalHelper.HideModal("modal2");
}
};
@@ -1,8 +1,7 @@
<template>
<modal type="modal-image" :title="title">
<button class="close" slot="header-buttons" @click="close()"><i class="fa fa-remove"></i></button>
<zoom-image :imageSrc="this.content" :showBackButton="false" />
<zoom-image :imageSrc="this.content" :showBackButton="false" :isTcam="true"/>
</modal>
</template>
<script src="./modal-image.ts" lang="ts" />
<!--<script src="./create-maintenance.ts" lang="ts"></script>-->
@@ -1,5 +1,7 @@
import Vue from "vue";
import { Prop, Component } from "vue-property-decorator";
import { warmersService } from "@/services/warmersService";
import { store } from '@/store';
@Component([])
export default class ZoomImage extends Vue {
@@ -9,6 +11,8 @@ export default class ZoomImage extends Vue {
imageSrc: string;
@Prop({ default: true })
showBackButton: boolean;
@Prop({ default: false })
isTcam: boolean;
transImage: string = "";
scaleImage: number = 1;
@@ -40,6 +44,10 @@ export default class ZoomImage extends Vue {
}
get thermocameraModeBTN(): boolean {
return (store.state.warmers.tCamStatus.thermoCamOnOff);
}
close() {
this.$emit("close");
}
@@ -136,5 +144,10 @@ export default class ZoomImage extends Vue {
this.transImage = "translateX(" + 0 + "px)translateY(" + 0 + "px)scale(" + this.scaleImage + ")";
}
async forceTakeImage() {
warmersService.TakeNewPhoto();
}
};
@@ -7,14 +7,19 @@
@touchstart="dw"
@touchmove="move"
@dblclick="zoomPlusAnimated">
<svg xmlns="http://www.w3.org/2000/svg" :style="{'transform':transImage}" v-html="imageSrc" version="1.1" width="100%" height="100%" viewBox="0 0 2000 1500" v-on:load="onImageLoaded"></svg>
<img ref="imageChild" :style="{'transform':transImage,'transition':animation}" :src="imageSrc" v-on:load="onImageLoaded" >
<!-- <svg xmlns="http://www.w3.org/2000/svg" :style="{'transform':transImage}" v-html="imageSrc" version="1.1" width="100%" height="100%" viewBox="0 0 2000 1500" v-on:load="onImageLoaded"></svg>-->
</div>
<!-- <div class="loading" v-if="!imageLoaded"><i class="fa fa-circle-o-notch fa-spin"></i></div>-->
<div class="loading" v-if="!imageLoaded"><i class="fa fa-circle-o-notch fa-spin"></i></div>
<div class="btngroup_close" v-if="showBackButton">
<button @click="close"><i class="fa fa-chevron-left" ></i></button>
</div>
<div class="btngroup2" v-if="true">
<button @click="forceTakeImage()" :disabled="thermocameraModeBTN">
<img src="/assets/icons/png/takesnap.png" />
</button>
</div>
<div class="btngroup">
<button @click="zoomPlusAnimated"><i class="fa fa-search-plus" ></i></button>
<div class="rangecontainer">
+22 -10
View File
@@ -113,6 +113,7 @@ export class Hub {
// qui i NUOVI metodi NUOVI dal server (Recipe, gauges) da completare lato HUB
this._hub.client.recipeFullData = Hub.recipeFullData;
this._hub.client.recipeFullDataInvalidSetpoint = Hub.recipeFullDataInvalidSetpoint;
this._hub.client.warmersData = Hub.warmersData;
this._hub.client.setpointHmiInvalid = Hub.setpointHmiInvalid;
this._hub.client.recipeOverData = Hub.recipeOverData;
@@ -124,8 +125,7 @@ export class Hub {
this._hub.client.gaugeData = Hub.gaugeData;
this._hub.client.axisInfo = Hub.axisInfoData;
this._hub.client.channelsIoVal = Hub.channelsIOUpdate;
this._hub.client.newThermoCamImage = Hub.newThermoCamImage;
this._hub.client.logout = this.logout;
@@ -140,20 +140,22 @@ export class Hub {
$.connection.hub.disconnected(() => {
Hub.manageServerStatus("disconnected");
console.log("SERVER CONNECTION: restart-connection")
setTimeout(function () {
$.connection.hub.start();
// $.connection.hub.start({ transport: ['serverSentEvents'] });
$.connection.hub.start({ transport: ['serverSentEvents'] });
}, 5000); // Restart connection after 5 seconds.
});
$.connection.hub.stateChanged(async (state) => {
if (state.newState == $.signalR.connectionState.connected) {
try {
await scadaService.ListScada();
}
catch (err)
{ }
Hub.manageServerStatus("connected");
}
})
$.connection.hub.start();
// $.connection.hub.start({ transport: ['serverSentEvents'] });
$.connection.hub.start({ transport: ['serverSentEvents'] });
this.checkShowAxes();
@@ -202,14 +204,17 @@ export class Hub {
recipeActions.setCurrent(store, data, true);
}
public static recipeFullDataInvalidSetpoint(data) {
recipeActions.setCurrent(store, data, false);
}
public static warmersData(data) {
warmersActions.setChannels(store, data as { [id: number]: Warmers.IChannel });
}
public static async setpointHmiInvalid(data) {
if (data) {
await recipeService.GetCurrent();
await warmersService.GetChannels();
await warmersService.GetThermocameraStatus();
// await recipeService.GetOverview();
}
@@ -219,6 +224,11 @@ export class Hub {
recipeActions.setOverview(store, data);
}
public static newThermoCamImage(data) {
messageService.publishToChannel("new-thermocam-image", data);
}
public static prodPanelData(data) {
prodActions.setProdPanel(store, data);
}
@@ -227,6 +237,8 @@ export class Hub {
prodActions.setProd(store, data);
}
public updateAuthToken() {
// Set or update authorization token
let authData = JSON.parse(window.localStorage.getItem("authorizationData") || window.sessionStorage.getItem("authorizationData")) as AuthToken;
@@ -239,6 +251,7 @@ export class Hub {
$.connection.hub.qs.CmsClientId = cmsClient.getClientID;
}
private logout(e) {
if (e)
appModelActions.CheckLogoff(store, e.id);
@@ -369,7 +382,6 @@ export class Hub {
var toast = document.querySelector('#serverConnection') as any;
(iziToast as any).hide(toast);
Hub._serverConnectionNotificationVisible = false;
try { await scadaService.ListScada(); } catch (err) { }
messageService.publishToChannel("force-ui-update", null);
}
}
@@ -43,6 +43,17 @@ export class UnderTheHoodService extends baseRestService {
return result;
}
async GetHistorySheetsCount() {
let result = await this.Get<number>((await this.BASE_URL()) + "/api/underthehood/SheetHistoryCount", true);
return result;
}
async GetHistorySheetsFitered(from,num) {
let result = await this.Get<number>((await this.BASE_URL()) + `/api/underthehood/SheetHistoryFiltered?start=${from}&number=${num}`, true);
return result;
}
}
export const underTheHoodService = new UnderTheHoodService();
@@ -71,10 +71,14 @@ export class WarmersService extends baseRestService {
let result = await this.Get<{
imageSize: { x: number, y: number },
rangeTemperature: { max: number, min: number },
thermoCamConnected: boolean,
thermoOptionActive: boolean,
lastTakenImage: Date,
}>((await this.BASE_URL()) + "TCamData", true);
return result;
}
async GetMeasurePoints(setname: string): Promise<any> {
return await this.Get<any>((await this.BASE_URL()) + `getMeasurePoints?setName=${setname}`, true);
}
@@ -86,5 +90,10 @@ export class WarmersService extends baseRestService {
async ResetMeasurePoints() {
return this.Put((await this.BASE_URL()) + `resetMeasurePoint`, null, true);
}
async TakeNewPhoto() {
return this.Put((await this.BASE_URL()) + `TakeTcamImage`, null, true);
}
}
export const warmersService = new WarmersService();