Compare commits

..

7 Commits

9 changed files with 88 additions and 79 deletions

View File

@ -81,6 +81,7 @@
<Compile Include="C3DeviceController.cs" /> <Compile Include="C3DeviceController.cs" />
<Compile Include="Camera.cs" /> <Compile Include="Camera.cs" />
<Compile Include="Enums.cs" /> <Compile Include="Enums.cs" />
<Compile Include="IDoorControlAccess.cs" />
<Compile Include="ILane.cs" /> <Compile Include="ILane.cs" />
<Compile Include="LaneIn.cs"> <Compile Include="LaneIn.cs">
<SubType>UserControl</SubType> <SubType>UserControl</SubType>

View File

@ -6,7 +6,7 @@ namespace AIParkingApplication
{ {
//@"C:\CongRa_1.mp4"; @"C:\HS_test.mp4"; @"rtsp://wowzaec2demo.streamlock.net/vod/mp4:BigBuckBunny_115k.mov" //@"C:\CongRa_1.mp4"; @"C:\HS_test.mp4"; @"rtsp://wowzaec2demo.streamlock.net/vod/mp4:BigBuckBunny_115k.mov"
private ApiController apiController; private ApiController apiController;
private C3DeviceController c3Device; private IDoorControlAccess c3Device;
private LaneIn laneIn; private LaneIn laneIn;
public AIParkingApplicationForm() public AIParkingApplicationForm()

View File

@ -4,6 +4,5 @@
{ {
public bool HasError { get; set; } public bool HasError { get; set; }
public string Message { get; set; } public string Message { get; set; }
public object Data { get; set; }
} }
} }

View File

@ -7,9 +7,9 @@ namespace AIParkingApplication
{ {
public delegate void C3DeviceEvent(int doorId, string cardNumber); public delegate void C3DeviceEvent(int doorId, string cardNumber);
public class C3DeviceController public class C3DeviceController : IDoorControlAccess
{ {
public string IPAddress { get; } private string ipAddress;
private int port; private int port;
private IntPtr oneTimeConnectedParamHandler; private IntPtr oneTimeConnectedParamHandler;
private string connectionString; private string connectionString;
@ -20,9 +20,9 @@ namespace AIParkingApplication
public C3DeviceController(string ipAddress, int port = C3Constant.DEFAULT_C3_PORT) public C3DeviceController(string ipAddress, int port = C3Constant.DEFAULT_C3_PORT)
{ {
IPAddress = ipAddress; this.ipAddress = ipAddress;
this.port = port; this.port = port;
connectionString = $"protocol=TCP,ipaddress={this.IPAddress},port={this.port},timeout=2000,passwd="; connectionString = $"protocol=TCP,ipaddress={this.ipAddress},port={this.port},timeout=2000,passwd=";
oneTimeConnectedParamHandler = IntPtr.Zero; oneTimeConnectedParamHandler = IntPtr.Zero;
isReconnected = true; isReconnected = true;
reconnectCounter = 0; reconnectCounter = 0;
@ -50,7 +50,7 @@ namespace AIParkingApplication
public ActionResult Connect() public ActionResult Connect()
{ {
if (Util.IsPingable(IPAddress, out long replyTime)) if (Util.IsPingable(ipAddress, out long replyTime))
{ {
oneTimeConnectedParamHandler = Connect(connectionString); oneTimeConnectedParamHandler = Connect(connectionString);
if (oneTimeConnectedParamHandler != IntPtr.Zero) if (oneTimeConnectedParamHandler != IntPtr.Zero)
@ -58,7 +58,7 @@ namespace AIParkingApplication
var result = new ActionResult var result = new ActionResult
{ {
HasError = false, HasError = false,
Message = string.Format(C3Constant.CONNECTED_SUCCESSFULLY, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), IPAddress) Message = string.Format(C3Constant.CONNECTED_SUCCESSFULLY, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), ipAddress)
}; };
return result; return result;
} }
@ -67,7 +67,7 @@ namespace AIParkingApplication
var result = new ActionResult var result = new ActionResult
{ {
HasError = true, HasError = true,
Message = string.Format(C3Constant.FAILED_TO_CONNECT, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), IPAddress, PullLastError()) Message = string.Format(C3Constant.FAILED_TO_CONNECT, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), ipAddress, PullLastError())
}; };
return result; return result;
} }
@ -77,7 +77,7 @@ namespace AIParkingApplication
var result = new ActionResult var result = new ActionResult
{ {
HasError = true, HasError = true,
Message = string.Format(C3Constant.FAILED_TO_PING, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), IPAddress) Message = string.Format(C3Constant.FAILED_TO_PING, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), ipAddress)
}; };
return result; return result;
} }
@ -93,7 +93,7 @@ namespace AIParkingApplication
var result = new ActionResult var result = new ActionResult
{ {
HasError = false, HasError = false,
Message = string.Format(C3Constant.OPENNED_DOOR_SUCCESSFULLY, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), IPAddress) Message = string.Format(C3Constant.OPENNED_DOOR_SUCCESSFULLY, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), ipAddress)
}; };
return result; return result;
} }
@ -102,7 +102,7 @@ namespace AIParkingApplication
var result = new ActionResult var result = new ActionResult
{ {
HasError = true, HasError = true,
Message = string.Format(C3Constant.FAILED_TO_OPEN_DOOR, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), IPAddress) Message = string.Format(C3Constant.FAILED_TO_OPEN_DOOR, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), ipAddress)
}; };
return result; return result;
} }
@ -112,7 +112,7 @@ namespace AIParkingApplication
var result = new ActionResult var result = new ActionResult
{ {
HasError = true, HasError = true,
Message = string.Format(C3Constant.NOT_CONNECTTED, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), IPAddress) Message = string.Format(C3Constant.NOT_CONNECTTED, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), ipAddress)
}; };
return result; return result;
} }
@ -131,18 +131,18 @@ namespace AIParkingApplication
} }
} }
public ActionResult GetRTLog(out int doorId, out string cardNumber) private ActionResult GetRTLog(out int doorId, out string cardNumber)
{ {
doorId = C3Constant.DEFAULT_DOOR_ID; doorId = C3Constant.DEFAULT_DOOR_ID;
cardNumber = C3Constant.DEFAULT_CARD_NUMBER; cardNumber = C3Constant.DEFAULT_CARD_NUMBER;
if (!Util.IsPingable(IPAddress, out long replyTime)) if (!Util.IsPingable(ipAddress, out long replyTime))
{ {
isReconnected = false; isReconnected = false;
var result = new ActionResult var result = new ActionResult
{ {
HasError = true, HasError = true,
Message = string.Format(C3Constant.FAILED_TO_PING, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), IPAddress) Message = string.Format(C3Constant.FAILED_TO_PING, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), ipAddress)
}; };
return result; return result;
} }
@ -177,7 +177,7 @@ namespace AIParkingApplication
{ {
isReconnected = true; isReconnected = true;
reconnectCounter = 0; reconnectCounter = 0;
reconnectResult.Message = string.Format(C3Constant.RECONNECTED_SUCCESSFULLY, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), IPAddress); reconnectResult.Message = string.Format(C3Constant.RECONNECTED_SUCCESSFULLY, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), ipAddress);
} }
return reconnectResult; return reconnectResult;
} }
@ -185,7 +185,7 @@ namespace AIParkingApplication
var result = new ActionResult var result = new ActionResult
{ {
HasError = true, HasError = true,
Message = string.Format(C3Constant.FAILED_TO_READ_LOG, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), IPAddress) Message = string.Format(C3Constant.FAILED_TO_READ_LOG, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), ipAddress)
}; };
return result; return result;
} }
@ -197,7 +197,7 @@ namespace AIParkingApplication
var result = new ActionResult var result = new ActionResult
{ {
HasError = true, HasError = true,
Message = string.Format(C3Constant.WRONG_FORMAT_DATA, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), IPAddress, ex.Message) Message = string.Format(C3Constant.WRONG_FORMAT_DATA, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), ipAddress, ex.Message)
}; };
return result; return result;
} }
@ -210,7 +210,7 @@ namespace AIParkingApplication
var result = new ActionResult var result = new ActionResult
{ {
HasError = false, HasError = false,
Message = string.Format(C3Constant.DISCONNECTED_SUCCESSFULLY, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), IPAddress) Message = string.Format(C3Constant.DISCONNECTED_SUCCESSFULLY, DateTime.Now.ToString(AppConstant.DATETIME_FORMAT), ipAddress)
}; };
return result; return result;
} }

View File

@ -0,0 +1,14 @@
using System.Threading.Tasks;
namespace AIParkingApplication
{
public interface IDoorControlAccess
{
event C3DeviceEvent OnNewCardReceived;
ActionResult Connect();
ActionResult Disconnect();
Task GetLogToReceiveNewCard();
ActionResult OpenDoor(int doorId);
}
}

View File

@ -18,13 +18,13 @@ namespace AIParkingApplication
private bool isSupportLongPlate; private bool isSupportLongPlate;
private bool isAutoOpenDoor; private bool isAutoOpenDoor;
private bool isRetryMode; private bool isRetryMode;
private C3DeviceController c3Device; private IDoorControlAccess doorControlAccess;
private ApiController apiController; private ApiController apiController;
public LaneIn(int doorId, public LaneIn(int doorId,
string plateStream, string plateStream,
string overviewStream, string overviewStream,
C3DeviceController c3Device, IDoorControlAccess doorControlAccess,
ApiController apiController, ApiController apiController,
bool isSupportSquarePlate = true, bool isSupportSquarePlate = true,
bool isSupportLongPlate = false, bool isSupportLongPlate = false,
@ -41,8 +41,8 @@ namespace AIParkingApplication
overviewCamera = new Camera(overviewStream); overviewCamera = new Camera(overviewStream);
plateCamera = new Camera(plateStream); plateCamera = new Camera(plateStream);
this.apiController = apiController; this.apiController = apiController;
this.c3Device = c3Device; this.doorControlAccess = doorControlAccess;
this.c3Device.OnNewCardReceived += C3Device_OnNewCardReceived; this.doorControlAccess.OnNewCardReceived += C3Device_OnNewCardReceived;
plateCamera.OnVideoFrameReceived += PlateCameraOnVideoFrameReceived; plateCamera.OnVideoFrameReceived += PlateCameraOnVideoFrameReceived;
plateCamera.OnOpenVideoStreamFailed += PlateCamera_OnOpenVideoStreamFailed; plateCamera.OnOpenVideoStreamFailed += PlateCamera_OnOpenVideoStreamFailed;
@ -115,7 +115,7 @@ namespace AIParkingApplication
private void OpenDoor(int doorId) private void OpenDoor(int doorId)
{ {
if (c3Device.OpenDoor(doorId).HasError) if (doorControlAccess.OpenDoor(doorId).HasError)
{ {
lblStatusInfo.UpdateLabel("KHÔNG THỂ MỞ CỬA", Color.Red); lblStatusInfo.UpdateLabel("KHÔNG THỂ MỞ CỬA", Color.Red);
} }
@ -163,10 +163,10 @@ namespace AIParkingApplication
private void ShowCardInfoOnUI(string cardNumber, string plateString, string cardType, string cardTime) private void ShowCardInfoOnUI(string cardNumber, string plateString, string cardType, string cardTime)
{ {
lblCardNumber.UpdateLabel($"Số thẻ: {cardNumber}", lblCardNumber.BackColor); lblCardNumber.UpdateLabel($"Số thẻ: {cardNumber}");
lblPlateString.UpdateLabel($"Biển số: {plateString}", lblPlateString.BackColor); lblPlateString.UpdateLabel($"Biển số: {plateString}");
lblCardType.UpdateLabel($"Loại thẻ: {cardType}", lblCardType.BackColor); lblCardType.UpdateLabel($"Loại thẻ: {cardType}");
lblCardTime.UpdateLabel($"Thời gian: {cardTime}", lblCardTime.BackColor); lblCardTime.UpdateLabel($"Thời gian: {cardTime}");
lblStatusInfo.UpdateLabel(string.IsNullOrEmpty(plateString) ? "KHÔNG NHẬN DIỆN ĐƯỢC BIỂN SỐ" : $"MỜI XE {plateString} VÀO", string.IsNullOrEmpty(plateString) ? Color.Red : Color.Green); lblStatusInfo.UpdateLabel(string.IsNullOrEmpty(plateString) ? "KHÔNG NHẬN DIỆN ĐƯỢC BIỂN SỐ" : $"MỜI XE {plateString} VÀO", string.IsNullOrEmpty(plateString) ? Color.Red : Color.Green);
} }
@ -196,9 +196,9 @@ namespace AIParkingApplication
private void ConnectToDoorAccessControl() private void ConnectToDoorAccessControl()
{ {
if (!this.c3Device.Connect().HasError) if (!this.doorControlAccess.Connect().HasError)
{ {
_ = this.c3Device.GetLogToReceiveNewCard(); _ = this.doorControlAccess.GetLogToReceiveNewCard();
} }
else else
{ {

View File

@ -2,13 +2,11 @@
using System.Windows.Forms; using System.Windows.Forms;
using System.Threading; using System.Threading;
using Newtonsoft.Json; using Newtonsoft.Json;
using System.Net.Http;
namespace AIParkingApplication namespace AIParkingApplication
{ {
public partial class Statistic : UserControl public partial class Statistic : UserControl
{ {
private readonly HttpClient client;
private readonly Thread thrStatistics; private readonly Thread thrStatistics;
private readonly TimeSpan updateInterval; private readonly TimeSpan updateInterval;
private ParkInfo parkInfo; private ParkInfo parkInfo;
@ -52,25 +50,12 @@ namespace AIParkingApplication
{ {
return; return;
} }
lblSoLuongXeMay.Invoke(new Action(() => lblSoLuongXeMay.UpdateLabel(parkInfo.NumberOfMoto.ToString());
{ lblSoLuongOto.UpdateLabel(parkInfo.NumberOfCar.ToString());
lblSoLuongXeMay.Text = parkInfo.NumberOfMoto.ToString(); lblVehicleTotalIn.UpdateLabel(parkInfo.TotalIn);
})); lblVehicleTotalOut.UpdateLabel(parkInfo.TotalOut);
lblSoLuongOto.Invoke(new Action(() =>
{
lblSoLuongOto.Text = parkInfo.NumberOfCar.ToString();
}));
lblVehicleTotalIn.Invoke(new Action(() =>
{
lblVehicleTotalIn.Text = parkInfo.TotalIn;
}));
lblVehicleTotalOut.Invoke(new Action(() =>
{
lblVehicleTotalOut.Text = parkInfo.TotalOut;
}));
} }
private void Statistic_Load(object sender, EventArgs e) private void Statistic_Load(object sender, EventArgs e)
{ {
tlpStatisticTable.BorderStyle = BorderStyle.FixedSingle; tlpStatisticTable.BorderStyle = BorderStyle.FixedSingle;
@ -90,8 +75,8 @@ namespace AIParkingApplication
tlpStatisticTable.Controls.Add(lblSoLuong, 1, 0); tlpStatisticTable.Controls.Add(lblSoLuong, 1, 0);
tlpStatisticTable.Controls.Add(lblSoLuongXeMay, 1, 1); tlpStatisticTable.Controls.Add(lblSoLuongXeMay, 1, 1);
tlpStatisticTable.Controls.Add(lblSoLuongOto, 1, 2); tlpStatisticTable.Controls.Add(lblSoLuongOto, 1, 2);
} }
public class ParkInfo public class ParkInfo
{ {
[JsonProperty("oto")] [JsonProperty("oto")]

View File

@ -1,19 +1,22 @@
using System; using System;
using System.Drawing; using System.Drawing;
using System.Windows.Forms;
using System.Threading; using System.Threading;
using System.Windows.Forms;
namespace AIParkingApplication namespace AIParkingApplication
{ {
public partial class StatusBar : UserControl public partial class StatusBar : UserControl
{ {
private string webServerIP; private string webServerIP;
private string c3IP; private string doorAccessControlDeviceIP;
public StatusBar(string webServerIP, string c3IP) private TimeSpan updateInterval;
public StatusBar(string webServerIP, string doorAccessControlDeviceIP, TimeSpan updateInterval)
{ {
InitializeComponent(); InitializeComponent();
this.webServerIP = webServerIP; this.webServerIP = webServerIP;
this.c3IP = c3IP; this.doorAccessControlDeviceIP = doorAccessControlDeviceIP;
this.updateInterval = updateInterval;
Thread thrStatus = new Thread(new ThreadStart(UpdateStatus)); Thread thrStatus = new Thread(new ThreadStart(UpdateStatus));
thrStatus.IsBackground = true; thrStatus.IsBackground = true;
thrStatus.Start(); thrStatus.Start();
@ -25,37 +28,25 @@ namespace AIParkingApplication
{ {
if (IsHandleCreated) if (IsHandleCreated)
{ {
lblDateTime.Invoke(new Action(() => lblDateTime.UpdateLabel(DateTime.Now.ToString(AppConstant.DATETIME_FORMAT));
{
lblDateTime.Text = DateTime.Now.ToString(AppConstant.DATETIME_FORMAT);
}));
lblPingTimeC3.Invoke(new Action(() => PingResult pingDoorAccessControlResult = GetPingStatus(doorAccessControlDeviceIP);
{ lblPingTimeC3.UpdateLabel($"{pingDoorAccessControlResult.ReplyTime} ms", pingDoorAccessControlResult.BackColor, pingDoorAccessControlResult.ForeColor);
PingResult pingResult = GetPingStatus(c3IP);
lblPingTimeC3.Text = $"{pingResult.ReplyTime} ms";
lblPingTimeC3.BackColor = pingResult.BackColor;
lblPingTimeC3.ForeColor = pingResult.ForceColor;
}));
lblPingTimeServer.Invoke(new Action(() => PingResult pingWebServerResult = GetPingStatus(webServerIP);
{ lblPingTimeServer.UpdateLabel($"{pingWebServerResult.ReplyTime} ms", pingWebServerResult.BackColor, pingWebServerResult.ForeColor);
PingResult pingResult = GetPingStatus(webServerIP);
lblPingTimeServer.Text = $"{pingResult.ReplyTime} ms";
lblPingTimeServer.BackColor = pingResult.BackColor;
lblPingTimeServer.ForeColor = pingResult.ForceColor;
}));
} }
Thread.Sleep(1000); Thread.Sleep(updateInterval);
} }
} }
private PingResult GetPingStatus(string ip) private PingResult GetPingStatus(string ipAddress)
{ {
PingResult pingResult = new PingResult(); PingResult pingResult = new PingResult();
bool isPingable; bool isPingable;
isPingable = Util.IsPingable(ip, out long replyTime); isPingable = Util.IsPingable(ipAddress, out long replyTime);
if (isPingable) if (isPingable)
{
switch (replyTime) switch (replyTime)
{ {
case long n when (n >= 0 && n < 1): case long n when (n >= 0 && n < 1):
@ -71,6 +62,7 @@ namespace AIParkingApplication
pingResult.BackColor = Color.Red; pingResult.BackColor = Color.Red;
break; break;
} }
}
else else
{ {
pingResult.ReplyTime = 0; pingResult.ReplyTime = 0;
@ -83,7 +75,7 @@ namespace AIParkingApplication
{ {
public long ReplyTime { get; set; } public long ReplyTime { get; set; }
public Color BackColor { get; set; } public Color BackColor { get; set; }
public Color ForceColor { get; set; } public Color ForeColor { get; set; }
} }
} }
} }

View File

@ -86,11 +86,29 @@ namespace AIParkingApplication
})); }));
} }
public static void UpdateLabel(this Label label, string text, Color color) public static void UpdateLabel(this Label label, string text, Color backColor, Color foreColor)
{
label.Invoke(new Action(() =>
{
label.Text = text;
label.BackColor = backColor;
label.ForeColor = foreColor;
}));
}
public static void UpdateLabel(this Label label, string text, Color backColor)
{
label.Invoke(new Action(() =>
{
label.Text = text;
label.BackColor = backColor;
}));
}
public static void UpdateLabel(this Label label, string text)
{ {
label.Invoke(new Action(() => label.Invoke(new Action(() =>
{ {
label.BackColor = color;
label.Text = text; label.Text = text;
})); }));
} }