integrado oid can

This commit is contained in:
Diego Freitas 2025-05-01 15:27:01 -03:00
parent fcd545a5b5
commit cae8b20601
60 changed files with 1198 additions and 743 deletions

Binary file not shown.

View File

@ -512,6 +512,7 @@
<Compile Include="Services\ModbusService.cs" />
<Compile Include="Services\MqttService.cs" />
<Compile Include="Services\OAKCameraService.cs" />
<Compile Include="Services\OIDCanService.cs" />
<Compile Include="Services\OIDService.cs" />
<Compile Include="Services\PythonService.cs" />
<Compile Include="Services\PZEMService.cs" />

View File

@ -71,7 +71,7 @@ namespace AgroBase.Forms.Direcional
cmb.SelectedItem = Enum.GetName(typeof(Sentido), sentido);
TextBox txtEndereco = FuncoesGlobais.FindControlRecursive<TextBox>(gpbSentido, "txt" + Modulo.Modulo_ID + "Endereco");
txtEndereco.Text = Modulo.DirMotor.Endereco;
txtEndereco.Text = FuncoesGlobais.HexByteToString(Modulo.DirMotor._EnderecoCAN_Tx);
NumericUpDown nudOffset = FuncoesGlobais.FindControlRecursive<NumericUpDown>(gpbSentido, "nud" + Modulo.Modulo_ID + "Offset");
nudOffset.Value = Convert.ToInt32(Modulo.DirMotor.FolgaMecanica);
@ -114,7 +114,7 @@ namespace AgroBase.Forms.Direcional
}
TextBox txtEndereco = FuncoesGlobais.FindControlRecursive<TextBox>(gpbSentido, "txt" + Modulo.Modulo_ID + "Endereco");
Modulo.DirMotor.Endereco = txtEndereco.Text;
Modulo.DirMotor._EnderecoCAN_Tx = FuncoesGlobais.StringToHexByte(txtEndereco.Text);
NumericUpDown nudOffset = FuncoesGlobais.FindControlRecursive<NumericUpDown>(gpbSentido, "nud" + Modulo.Modulo_ID + "Offset");
Modulo.DirMotor.FolgaMecanica = Convert.ToDouble(nudOffset.Value);

View File

@ -12,6 +12,7 @@ using System.Linq;
using System.Threading.Tasks;
using System.Windows.Forms;
using static AgroBase.Models.Enums;
using static AgroBase.Services.OIDCanService.OidHandler;
namespace AgroBase.Forms.IHM
{
@ -746,7 +747,7 @@ namespace AgroBase.Forms.IHM
double TemperaturaDriver = Inicializado ? Modulo.MovMotor.TemperaturaDriver : -1;
idx = PreencheDadosLinha(grid, Testes, idx, TemperaturaDriver);
double CodigoErro = Inicializado ? Modulo.MovMotor.CodigoAlarme : -1;
int CodigoErro = Inicializado ? (int)Modulo.MovMotor.CodigoAlarme : (int)OidCodigoErro.NenhumErro;
idx = PreencheDadosLinha(grid, Testes, idx, CodigoErro);
bool ParaFrente = Inicializado ? await EnviarComandoMov(Modulo, Enums.Direcao.Frente, Testes[idx], 5000) : false;
@ -837,7 +838,7 @@ namespace AgroBase.Forms.IHM
bool Sucesso = false;
while (!Sucesso && Inicio.AddMilliseconds(Timeout) > DateTime.Now)
{
Dispositivo.Dados.RequisitarDadosModulo(F_Code.ReqTx, ServoFreio.ID_Num, CanMessagePosicaoDados.Dados1);
Dispositivo.Dados.RequisitarDadosModulo(ServoFreio.ID_Num, CanMessagePosicaoDados.Dados1, CanMessagePosicaoDados.Dados1, true);
await Task.Delay(1000);
Sucesso =
@ -1453,7 +1454,7 @@ namespace AgroBase.Forms.IHM
var novoEstado = Ligar ? Estado.Ligado : Estado.Desligado;
GeneralJoystick.EnviarComandoSensoriamento(S_Code.sRLE, Rele.ID, novoEstado);
await Task.Delay(Delay);
Dispositivo.Dados.RequisitarDadosModulo(F_Code.ReqTx, Rele.ID_Num, CanMessagePosicaoDados.Dados1);
Dispositivo.Dados.RequisitarDadosModulo(Rele.ID_Num, CanMessagePosicaoDados.Dados1, CanMessagePosicaoDados.Dados1, true);
await Task.Delay(Delay);
}
@ -1714,7 +1715,7 @@ namespace AgroBase.Forms.IHM
Comportamento.statusLED = Ligar ? StatusLED.Aceso : StatusLED.Apagado;
GeneralJoystick.EnviarComandoSensoriamento(S_Code.sLED, Sinaleiro.ID, Comportamento);
await Task.Delay(Delay);
Dispositivo.Dados.RequisitarDadosModulo(F_Code.ReqTx, Sinaleiro.ID_Num, CanMessagePosicaoDados.Dados1);
Dispositivo.Dados.RequisitarDadosModulo(Sinaleiro.ID_Num, CanMessagePosicaoDados.Dados1, CanMessagePosicaoDados.Dados1, true);
await Task.Delay(Delay);
}

View File

@ -70,7 +70,7 @@ namespace AgroBase.Forms.Movimentacao
txtTorqueMaximo.Text = Modulo.MovMotor.CorrenteTorqueMaximo.ToString();
TextBox txtEndereco = FuncoesGlobais.FindControlRecursive<TextBox>(gpbSentido, "txt" + Modulo.Modulo_ID + "Endereco");
txtEndereco.Text = Modulo.MovMotor.Endereco;
txtEndereco.Text = FuncoesGlobais.HexByteToString(Modulo.MovMotor._EnderecoCAN_Tx);
GroupBox gpbFreio = FuncoesGlobais.FindControlRecursive<GroupBox>(gpbSentido, "gpb" + Mod_ID + "_Freio");
if (gpbFreio != null)
@ -129,7 +129,7 @@ namespace AgroBase.Forms.Movimentacao
Modulo.MovMotor.CorrenteTorqueMaximo = Convert.ToInt32(txtTorqueMaximo.Text);
TextBox txtEndereco = FuncoesGlobais.FindControlRecursive<TextBox>(gpbSentido, "txt" + Modulo.Modulo_ID + "Endereco");
Modulo.MovMotor.Endereco = txtEndereco.Text;
Modulo.MovMotor._EnderecoCAN_Tx = FuncoesGlobais.StringToHexByte(txtEndereco.Text);
GroupBox gpbFreio = FuncoesGlobais.FindControlRecursive<GroupBox>(gpbSentido, "gpb" + Modulo.Modulo_ID + "_Freio");
if (gpbFreio != null)

View File

@ -60,10 +60,12 @@
this.lblCaminho = new System.Windows.Forms.Label();
this.cmbCaminho = new System.Windows.Forms.ComboBox();
this.chbRequisitarDados = new System.Windows.Forms.CheckBox();
this.lblIP = new System.Windows.Forms.Label();
this.txtEnderecoCAN = new System.Windows.Forms.TextBox();
this.lblAddrTx = new System.Windows.Forms.Label();
this.txtEnderecoCAN_Tx = new System.Windows.Forms.TextBox();
this.lblPotenciometro = new System.Windows.Forms.Label();
this.gridsPOT = new System.Windows.Forms.DataGridView();
this.lblAddrRx = new System.Windows.Forms.Label();
this.txtEnderecoCAN_Rx = new System.Windows.Forms.TextBox();
((System.ComponentModel.ISupportInitialize)(this.gridsTEN)).BeginInit();
((System.ComponentModel.ISupportInitialize)(this.gridsCOR)).BeginInit();
((System.ComponentModel.ISupportInitialize)(this.gridsTMP)).BeginInit();
@ -381,33 +383,33 @@
//
this.chbRequisitarDados.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Right)));
this.chbRequisitarDados.AutoSize = true;
this.chbRequisitarDados.Location = new System.Drawing.Point(1100, 628);
this.chbRequisitarDados.Location = new System.Drawing.Point(1100, 664);
this.chbRequisitarDados.Name = "chbRequisitarDados";
this.chbRequisitarDados.Size = new System.Drawing.Size(107, 17);
this.chbRequisitarDados.TabIndex = 28;
this.chbRequisitarDados.Text = "Requisitar Dados";
this.chbRequisitarDados.UseVisualStyleBackColor = true;
//
// lblIP
// lblAddrTx
//
this.lblIP.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Right)));
this.lblIP.AutoSize = true;
this.lblIP.Location = new System.Drawing.Point(1097, 579);
this.lblIP.Margin = new System.Windows.Forms.Padding(2, 0, 2, 0);
this.lblIP.Name = "lblIP";
this.lblIP.Size = new System.Drawing.Size(78, 13);
this.lblIP.TabIndex = 145;
this.lblIP.Text = "Endereço CAN";
this.lblAddrTx.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Right)));
this.lblAddrTx.AutoSize = true;
this.lblAddrTx.Location = new System.Drawing.Point(1097, 579);
this.lblAddrTx.Margin = new System.Windows.Forms.Padding(2, 0, 2, 0);
this.lblAddrTx.Name = "lblAddrTx";
this.lblAddrTx.Size = new System.Drawing.Size(69, 13);
this.lblAddrTx.TabIndex = 145;
this.lblAddrTx.Text = "CAN Addr Tx";
//
// txtEnderecoCAN
// txtEnderecoCAN_Tx
//
this.txtEnderecoCAN.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Right)));
this.txtEnderecoCAN.Location = new System.Drawing.Point(1100, 596);
this.txtEnderecoCAN.Margin = new System.Windows.Forms.Padding(2);
this.txtEnderecoCAN.Name = "txtEnderecoCAN";
this.txtEnderecoCAN.Size = new System.Drawing.Size(85, 20);
this.txtEnderecoCAN.TabIndex = 144;
this.txtEnderecoCAN.TextAlign = System.Windows.Forms.HorizontalAlignment.Center;
this.txtEnderecoCAN_Tx.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Right)));
this.txtEnderecoCAN_Tx.Location = new System.Drawing.Point(1100, 596);
this.txtEnderecoCAN_Tx.Margin = new System.Windows.Forms.Padding(2);
this.txtEnderecoCAN_Tx.Name = "txtEnderecoCAN_Tx";
this.txtEnderecoCAN_Tx.Size = new System.Drawing.Size(85, 20);
this.txtEnderecoCAN_Tx.TabIndex = 144;
this.txtEnderecoCAN_Tx.TextAlign = System.Windows.Forms.HorizontalAlignment.Center;
//
// lblPotenciometro
//
@ -427,15 +429,38 @@
this.gridsPOT.Size = new System.Drawing.Size(578, 124);
this.gridsPOT.TabIndex = 146;
//
// lblAddrRx
//
this.lblAddrRx.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Right)));
this.lblAddrRx.AutoSize = true;
this.lblAddrRx.Location = new System.Drawing.Point(1097, 618);
this.lblAddrRx.Margin = new System.Windows.Forms.Padding(2, 0, 2, 0);
this.lblAddrRx.Name = "lblAddrRx";
this.lblAddrRx.Size = new System.Drawing.Size(70, 13);
this.lblAddrRx.TabIndex = 149;
this.lblAddrRx.Text = "CAN Addr Rx";
//
// txtEnderecoCAN_Rx
//
this.txtEnderecoCAN_Rx.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Right)));
this.txtEnderecoCAN_Rx.Location = new System.Drawing.Point(1100, 635);
this.txtEnderecoCAN_Rx.Margin = new System.Windows.Forms.Padding(2);
this.txtEnderecoCAN_Rx.Name = "txtEnderecoCAN_Rx";
this.txtEnderecoCAN_Rx.Size = new System.Drawing.Size(85, 20);
this.txtEnderecoCAN_Rx.TabIndex = 148;
this.txtEnderecoCAN_Rx.TextAlign = System.Windows.Forms.HorizontalAlignment.Center;
//
// frmSenConfig
//
this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
this.ClientSize = new System.Drawing.Size(1226, 730);
this.Controls.Add(this.lblAddrRx);
this.Controls.Add(this.txtEnderecoCAN_Rx);
this.Controls.Add(this.lblPotenciometro);
this.Controls.Add(this.gridsPOT);
this.Controls.Add(this.lblIP);
this.Controls.Add(this.txtEnderecoCAN);
this.Controls.Add(this.lblAddrTx);
this.Controls.Add(this.txtEnderecoCAN_Tx);
this.Controls.Add(this.chbRequisitarDados);
this.Controls.Add(this.gpbCameras);
this.Controls.Add(this.gpbBateria);
@ -510,9 +535,11 @@
private System.Windows.Forms.Button btnBateriaCalibrar;
private System.Windows.Forms.Button btnAtualizarCameras;
private System.Windows.Forms.CheckBox chbRequisitarDados;
private System.Windows.Forms.Label lblIP;
private System.Windows.Forms.TextBox txtEnderecoCAN;
private System.Windows.Forms.Label lblAddrTx;
private System.Windows.Forms.TextBox txtEnderecoCAN_Tx;
private System.Windows.Forms.Label lblPotenciometro;
private System.Windows.Forms.DataGridView gridsPOT;
private System.Windows.Forms.Label lblAddrRx;
private System.Windows.Forms.TextBox txtEnderecoCAN_Rx;
}
}

View File

@ -52,7 +52,8 @@ namespace AgroBase.Forms.Sensoriamento
}
}
txtEnderecoCAN.Text = Disp.Dados._EnderecoCAN.ToString("X");
txtEnderecoCAN_Tx.Text = FuncoesGlobais.HexByteToString(Disp.Dados._EnderecoCAN_Tx);
txtEnderecoCAN_Rx.Text = FuncoesGlobais.HexByteToString(Disp.Dados._EnderecoCAN_Rx);
PopulaParametrosSensor();
@ -196,7 +197,8 @@ namespace AgroBase.Forms.Sensoriamento
case T_Code.Sen:
{
var _Disp = (DispositivosService<SensoriamentoModel>)Variaveis.DispositivosConectados.FirstOrDefault(x => x.Dispositivo == Dispositivo);
_Disp.Dados._EnderecoCAN = Convert.ToByte(txtEnderecoCAN.Text, 16);
_Disp.Dados._EnderecoCAN_Tx = FuncoesGlobais.StringToHexByte(txtEnderecoCAN_Tx.Text);
_Disp.Dados._EnderecoCAN_Rx = FuncoesGlobais.StringToHexByte(txtEnderecoCAN_Rx.Text);
_Disp.Dados.RequisitarDados = chbRequisitarDados.Checked;
_Disp.Dados.Sensores = Sensores.ToList();
_Disp.Dados.CameraID_Caminho = cmbCaminho.Text;
@ -208,7 +210,8 @@ namespace AgroBase.Forms.Sensoriamento
case T_Code.Atu:
{
var _Disp = (DispositivosService<AtuadorModel>)Variaveis.DispositivosConectados.FirstOrDefault(x => x.Dispositivo == Dispositivo);
_Disp.Dados._EnderecoCAN = Convert.ToByte(txtEnderecoCAN.Text, 16);
_Disp.Dados._EnderecoCAN_Tx = FuncoesGlobais.StringToHexByte(txtEnderecoCAN_Tx.Text);
_Disp.Dados._EnderecoCAN_Rx = FuncoesGlobais.StringToHexByte(txtEnderecoCAN_Rx.Text);
_Disp.Dados.RequisitarDados = chbRequisitarDados.Checked;
_Disp.Dados.Sensores = Sensores.ToList();
_Disp.SalvarParametros(_Disp.Dados);

View File

@ -106,7 +106,7 @@ namespace AgroBase.Forms
Label lblTitulo = pnlFundo.Controls.OfType<Label>().FirstOrDefault(ctrl => ctrl.Name == "lblM_" + Modulo.Modulo_ID);
lblTitulo.ForeColor = Modulo.MovMotor.Comandar ? Modulo.MovMotor.Inicializado ? Color.Green : Color.Red : Color.Black;
lblTitulo.Text = lblTitulo.Text.Split(' ')[0] + " (" + Modulo.Modulo_ID + ") - Alm: " + Modulo.MovMotor.CodigoAlarme;
lblTitulo.Text = lblTitulo.Text.Split(' ')[0] + " (" + Modulo.Modulo_ID + ") - " + Modulo.MovMotor.CodigoAlarme;
Label lblM_RPMSP = pnlFundo.Controls.OfType<Label>().FirstOrDefault(ctrl => ctrl.Name == "lbl" + Modulo.Modulo_ID + "M_RPMSP");
lblM_RPMSP.Text = "RPM SP: " + Modulo.MovMotor.RPM_SP_Leitura.ToString("0.00");
Label lblM_RPM = pnlFundo.Controls.OfType<Label>().FirstOrDefault(ctrl => ctrl.Name == "lbl" + Modulo.Modulo_ID + "M_RPM");

View File

@ -2264,7 +2264,7 @@ namespace AgroBase.Forms
private async void btnIniciarRef_Click(object sender, EventArgs e)
{
//await ReferenciaMotor();
var Mod = Variaveis.OperacaoEmAndamento.DispMvd.Dados.Modulos.FirstOrDefault(x => x.DirMotor.Endereco == cmbEndereco.Text);
var Mod = Variaveis.OperacaoEmAndamento.DispMvd.Dados.Modulos.FirstOrDefault(x => x.DirMotor._EnderecoCAN_Tx == FuncoesGlobais.StringToHexByte(cmbEndereco.Text));
if (Mod != null)
{
await Mod.DirMotor.ReferenciaMotor();
@ -2382,7 +2382,8 @@ namespace AgroBase.Forms
if (CanService.IsConnected)
{
MKS057DCanService.RequisitarDado(Convert.ToByte(cmbEndereco.Text), MKS057DCanService.MksHandler.MksFuncCode.Versao);
byte addr = FuncoesGlobais.StringToHexByte(cmbEndereco.Text);
MKS057DCanService.RequisitarDado(addr, addr, MKS057DCanService.MksHandler.MksFuncCode.Versao);
}
return CanService.IsConnected;
@ -2397,7 +2398,8 @@ namespace AgroBase.Forms
Sentido sentido = rdbHorarioPosicao.Checked ? Sentido.Horario : Sentido.Antihorario;
ModosControle modo = (ModosControle)(cmbModo.SelectedIndex + 1);
MKS057DCanService.Movimento(Convert.ToByte(cmbEndereco.Text), angulo, (int)velocidade, sentido, modo);
byte addr = FuncoesGlobais.StringToHexByte(cmbEndereco.Text);
MKS057DCanService.Movimento(addr, addr, angulo, (int)velocidade, sentido, modo);
}
}
@ -2405,7 +2407,8 @@ namespace AgroBase.Forms
{
if (MKSIniciado())
{
MKS057DCanService.SetZero(Convert.ToByte(cmbEndereco.Text));
byte addr = FuncoesGlobais.StringToHexByte(cmbEndereco.Text);
MKS057DCanService.SetZero(addr, addr);
}
}
@ -2435,13 +2438,14 @@ namespace AgroBase.Forms
if (MKSIniciado())
{
MKS057DCanService.RequisitarDado(Convert.ToByte(cmbEndereco.Text), MKS057DCanService.MksHandler.MksFuncCode.PulsosRecebidos);
byte addr = FuncoesGlobais.StringToHexByte(cmbEndereco.Text);
MKS057DCanService.RequisitarDado(addr, addr, MKS057DCanService.MksHandler.MksFuncCode.PulsosRecebidos);
//mks.RequisitarDado(endereco, MKS057DCanService.MksHandler.MksFuncCode.EncoderCarregado);
//mks.RequisitarDado(endereco, MKS057DCanService.MksHandler.MksFuncCode.EncoderAcumulado);
MKS057DCanService.RequisitarDado(Convert.ToByte(cmbEndereco.Text), MKS057DCanService.MksHandler.MksFuncCode.IO);
MKS057DCanService.RequisitarDado(addr, addr, MKS057DCanService.MksHandler.MksFuncCode.IO);
//mks.RequisitarDado(endereco, MKS057DCanService.MksHandler.MksFuncCode.RPM);
dadosLeitura = MKS057DCanService.DadosLeitura.FirstOrDefault(x => x.Endereco == Convert.ToByte(cmbEndereco.Text));
dadosLeitura = MKS057DCanService.DadosLeitura.FirstOrDefault(x => x.EnderecoTx == FuncoesGlobais.StringToHexByte(cmbEndereco.Text));
if (dadosLeitura != null)
{

View File

@ -40,7 +40,7 @@ namespace AgroBase.Forms
AguardaResposta = aguarda,
TamanhoEsperado = tamanho,
Get = get,
Parametro = OIDService.Parametros.First(x => x.Chave == parametro),
Parametro = OIDRs485Service.Parametros.First(x => x.Chave == parametro),
};
if (val != null)
@ -48,7 +48,7 @@ namespace AgroBase.Forms
Comando.Valor = (float)val;
}
await OIDService.EnviarComandoControle(Comando);
await OIDRs485Service.EnviarComandoControle(Comando);
txtConsole.Text += SerialService.MostrarComandoResposta(Enums.T_Code.Oid, Comando.Comando, Comando.Resposta) + Environment.NewLine;
}
@ -56,43 +56,43 @@ namespace AgroBase.Forms
private async void btnERPM_Click(object sender, EventArgs e)
{
await EnviarComando(true, 9, "VelocidadeAngular");
txtERPM.Text = (OIDService.DadosLeitura.FirstOrDefault(x => x.Endereco == Addr)?.ERPM ?? 0).ToString();
txtERPM.Text = (OIDRs485Service.DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Addr)?.ERPM ?? 0).ToString();
}
private async void button3_Click(object sender, EventArgs e)
{
await EnviarComando(true, 9, "CorrenteMotor");
txtCorrente.Text = (OIDService.DadosLeitura.FirstOrDefault(x => x.Endereco == Addr)?.CorrenteMotor ?? 0).ToString();
txtCorrente.Text = (OIDRs485Service.DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Addr)?.CorrenteMotor ?? 0).ToString();
}
private async void button4_Click(object sender, EventArgs e)
{
await EnviarComando(true, 9, "Tensao");
txtTensao.Text = (OIDService.DadosLeitura.FirstOrDefault(x => x.Endereco == Addr)?.Tensao ?? 0).ToString();
txtTensao.Text = (OIDRs485Service.DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Addr)?.Tensao ?? 0).ToString();
}
private async void button5_Click(object sender, EventArgs e)
{
await EnviarComando(true, 9, "Potencia");
txtPotencia.Text = (OIDService.DadosLeitura.FirstOrDefault(x => x.Endereco == Addr)?.Potencia ?? 0).ToString();
txtPotencia.Text = (OIDRs485Service.DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Addr)?.Potencia ?? 0).ToString();
}
private async void button6_Click(object sender, EventArgs e)
{
await EnviarComando(true, 9, "CicloTrabalho");
txtCicloTrabalho.Text = (OIDService.DadosLeitura.FirstOrDefault(x => x.Endereco == Addr)?.CicloTrabalho ?? 0).ToString();
txtCicloTrabalho.Text = (OIDRs485Service.DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Addr)?.CicloTrabalho ?? 0).ToString();
}
private async void button7_Click(object sender, EventArgs e)
{
await EnviarComando(true, 7, "Temperatura");
txtTemperatura.Text = (OIDService.DadosLeitura.FirstOrDefault(x => x.Endereco == Addr)?.Temperatura ?? 0).ToString();
txtTemperatura.Text = (OIDRs485Service.DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Addr)?.Temperatura ?? 0).ToString();
}
private async void button1_Click(object sender, EventArgs e)
{
await EnviarComando(true, 7, "CodErro");
txtCodErro.Text = (OIDService.DadosLeitura.FirstOrDefault(x => x.Endereco == Addr)?.CodigoAlarme ?? 0).ToString();
txtCodErro.Text = (OIDRs485Service.DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Addr)?.CodigoAlarme ?? 0).ToString();
}
private async void button2_Click(object sender, EventArgs e)
@ -119,8 +119,8 @@ namespace AgroBase.Forms
private async void timer1_Tick(object sender, EventArgs e)
{
var p = OIDService.Parametros.First(x => x.Chave == "Heartbeat");
int v = OIDService.DadosLeitura.FirstOrDefault(x => x.Endereco == Addr)?.Heartbeat ?? 0;
var p = OIDRs485Service.Parametros.First(x => x.Chave == "Heartbeat");
int v = OIDRs485Service.DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Addr)?.Heartbeat ?? 0;
int nV = v == 0 ? 1 : 0;
await EnviarComando(false, 7, "Heartbeat", false, nV);
}
@ -195,13 +195,13 @@ namespace AgroBase.Forms
private void timer2_Tick(object sender, EventArgs e)
{
txtERPM.Text = (OIDService.DadosLeitura.FirstOrDefault(x => x.Endereco == Addr)?.ERPM ?? 0).ToString();
txtCorrente.Text = (OIDService.DadosLeitura.FirstOrDefault(x => x.Endereco == Addr)?.CorrenteMotor ?? 0).ToString();
txtTensao.Text = (OIDService.DadosLeitura.FirstOrDefault(x => x.Endereco == Addr)?.Tensao ?? 0).ToString();
txtPotencia.Text = (OIDService.DadosLeitura.FirstOrDefault(x => x.Endereco == Addr)?.Potencia ?? 0).ToString();
txtCicloTrabalho.Text = (OIDService.DadosLeitura.FirstOrDefault(x => x.Endereco == Addr)?.CicloTrabalho ?? 0).ToString();
txtTemperatura.Text = (OIDService.DadosLeitura.FirstOrDefault(x => x.Endereco == Addr)?.Temperatura ?? 0).ToString();
txtCodErro.Text = (OIDService.DadosLeitura.FirstOrDefault(x => x.Endereco == Addr)?.CodigoAlarme ?? 0).ToString();
txtERPM.Text = (OIDRs485Service.DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Addr)?.ERPM ?? 0).ToString();
txtCorrente.Text = (OIDRs485Service.DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Addr)?.CorrenteMotor ?? 0).ToString();
txtTensao.Text = (OIDRs485Service.DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Addr)?.Tensao ?? 0).ToString();
txtPotencia.Text = (OIDRs485Service.DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Addr)?.Potencia ?? 0).ToString();
txtCicloTrabalho.Text = (OIDRs485Service.DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Addr)?.CicloTrabalho ?? 0).ToString();
txtTemperatura.Text = (OIDRs485Service.DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Addr)?.Temperatura ?? 0).ToString();
txtCodErro.Text = (OIDRs485Service.DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Addr)?.CodigoAlarme ?? 0).ToString();
}
private void checkBox2_CheckedChanged(object sender, EventArgs e)

View File

@ -669,7 +669,8 @@ namespace AgroBase
}
var DispAtu = Variaveis.OperacaoEmAndamento.DispAtu;
F_Code fcode = F_Code.Nda;
int id_num = -1;
CanMessagePosicaoDados posicao = CanMessagePosicaoDados.Command1;
byte[] data = null;
switch (Componente)
@ -679,7 +680,7 @@ namespace AgroBase
if (Bomba != null)
{
Bomba.ComandoAtuar = Status;
(fcode, data) = Bomba.ProtocoloComando();
(id_num, posicao, data) = Bomba.ProtocoloComando();
}
break;
case S_Code.sBIC:
@ -687,12 +688,12 @@ namespace AgroBase
if (Bico != null)
{
Bico.ComandoAtuar = Status;
(fcode, data) = Bico.ProtocoloComando();
(id_num, posicao, data) = Bico.ProtocoloComando();
}
break;
}
DispAtu.AdicionarMensagemFila(fcode, data, false);
DispAtu.AdicionarMensagemFila(id_num, posicao, posicao, data, false);
}
@ -700,7 +701,8 @@ namespace AgroBase
{
var DispSen = Variaveis.OperacaoEmAndamento.DispSen;
F_Code fcode = F_Code.Nda;
int id_num = -1;
CanMessagePosicaoDados posicao = CanMessagePosicaoDados.Command1;
byte[] data = null;
switch (Componente)
@ -710,7 +712,7 @@ namespace AgroBase
if (Sinaleiro != null)
{
Sinaleiro.Comportamento = (SensorSinaleiroComportamentoModel)Status;
(fcode, data) = Sinaleiro.ProtocoloComando();
(id_num, posicao, data) = Sinaleiro.ProtocoloComando();
}
break;
case S_Code.sRLE:
@ -718,7 +720,7 @@ namespace AgroBase
if (Rele != null)
{
Rele.StatusControle = (Estado)Status;
(fcode, data) = Rele.ProtocoloComando();
(id_num, posicao, data) = Rele.ProtocoloComando();
}
break;
case S_Code.sFRO:
@ -726,12 +728,12 @@ namespace AgroBase
if (ServoFreio != null)
{
ServoFreio._AnguloControle = (int)Status;
(fcode, data) = ServoFreio.ProtocoloComando();
(id_num, posicao, data) = ServoFreio.ProtocoloComando();
}
break;
}
DispSen.AdicionarMensagemFila(fcode, data, false);
DispSen.AdicionarMensagemFila(id_num, posicao, posicao, data, false);
}
private static void AtualizaConsole(string Mensagem)

View File

@ -7,7 +7,8 @@ namespace AgroBase.Models
{
public class MKS057DModel
{
public byte Endereco { get; set; }
public byte EnderecoTx { get; set; }
public byte EnderecoRx { get; set; }
public bool Iniciado
{
get

View File

@ -16,7 +16,8 @@ namespace AgroBase.Models.Modules
{
public T_Code Dispositivo { get; set; } = T_Code.Atu;
public string Modulo_ID { get; set; } = T_Code.Atu.ToString();
public byte _EnderecoCAN { get; set; } = 0x12;
public byte _EnderecoCAN_Tx { get; set; } = 0x13;
public byte _EnderecoCAN_Rx { get; set; } = 0x14;
public int _TaxaAmostragem { get; set; } = 1000;
public bool RequisitarDados { get; set; } = true;
public static int PingsConsiderarConexao { get; set; } = 5;
@ -214,7 +215,8 @@ namespace AgroBase.Models.Modules
{
AtuadorModel Atuador = new AtuadorModel()
{
_EnderecoCAN = 0x12,
_EnderecoCAN_Tx = 0x13,
_EnderecoCAN_Rx = 0x14,
_TaxaAmostragem = 1000,
RequisitarDados = true,
QuantidadeBicos = 4,
@ -268,6 +270,16 @@ namespace AgroBase.Models.Modules
},
UnidadeMedida = "Kg",
Parametros = new List<SensorParametroModel>()
{
new SensorParametroModel()
{
Descricao = "Offset",
Enviar = true,
Escalar = false,
QtdBytes = 2,
Valor = "1895800"
}
}
},
new SensorModel()
{
@ -383,11 +395,11 @@ namespace AgroBase.Models.Modules
CanService.DefinirPortaCOM(porta);
}
CanService.RegistrarHandler((byte)((int)_EnderecoCAN + 1), _AtuHandler);
CanService.RegistrarHandler(_EnderecoCAN_Rx, _AtuHandler);
if (CanService.IsConnected)
{
RequisitarDadosModulo(F_Code.ChkTx);
RequisitarDadosModulo(Variaveis.ID_Num_sMOD, CanMessagePosicaoDados.Status, CanMessagePosicaoDados.Status, true);
await Task.Delay(1000);
@ -425,15 +437,15 @@ namespace AgroBase.Models.Modules
}
}
public void RequisitarDadosModulo(F_Code dado, bool aguardaResposta = true)
public void RequisitarDadosModulo(int ID_Num, CanMessagePosicaoDados posicaoTx, CanMessagePosicaoDados posicaoRx, bool aguardaResposta)
{
Variaveis.OperacaoEmAndamento.DispAtu?.AdicionarMensagemFila(dado, null, aguardaResposta);
Variaveis.OperacaoEmAndamento.DispAtu?.AdicionarMensagemFila(ID_Num, posicaoTx, posicaoRx, null, aguardaResposta);
}
public List<byte[]> ProtocoloConfiguracao(bool Conectar)
public List<(int, CanMessagePosicaoDados, byte[])> ProtocoloConfiguracao(bool Conectar)
{
// Inicializar o dicionário
List<byte[]> config = new List<byte[]>();
List<(int, CanMessagePosicaoDados, byte[])> config = new List<(int, CanMessagePosicaoDados, byte[])>();
if (!DadosLeitura.Conectado)
{
@ -445,50 +457,42 @@ namespace AgroBase.Models.Modules
bool configurarTodos = !DadosLeitura.Conectado && Conectar;
// Adicionar configurações dos Sensores que devem ser aferidos
List<byte[]> sensoresConfig = SensoresConfig(Conectar, configurarTodos);
var sensoresConfig = SensoresConfig(Conectar, configurarTodos);
config.AddRange(sensoresConfig);
// Adicionar configurações dos Bicos
List<byte[]> bicosConfig = BicosConfig(Conectar, configurarTodos);
var bicosConfig = BicosConfig(Conectar, configurarTodos);
config.AddRange(bicosConfig);
// Adicionar configurações das Bombas
List<byte[]> bombasConfig = BombasConfig(Conectar, configurarTodos);
var bombasConfig = BombasConfig(Conectar, configurarTodos);
config.AddRange(bombasConfig);
return config;
}
private List<byte[]> ModConfig(bool Conectar)
private List<(int, CanMessagePosicaoDados, byte[])> ModConfig(bool Conectar)
{
var config1 = new List<byte>
{
Variaveis.ID_Num_sMOD,
(byte)CanMessagePosicaoDados.Config1,
(byte)S_Code.sMOD,
(byte)(Conectar ? 1 : 0),
(byte)(_TaxaAmostragem / 10),
(byte)(RequisitarDados ? 1 : 0),
};
var config2 = new List<byte>
{
Variaveis.ID_Num_sMOD,
(byte)CanMessagePosicaoDados.Config2,
(byte)S_Code.sMOD,
};
var config2 = new List<byte>();
config2.AddRange(PinoutModel.PinoProtocolo(Pinout, Funcoes, false));
return new List<byte[]>
return new List<(int, CanMessagePosicaoDados, byte[])>
{
config1.ToArray(),
config2.ToArray()
(Variaveis.ID_Num_sMOD, CanMessagePosicaoDados.Config1, config1.ToArray()),
(Variaveis.ID_Num_sMOD, CanMessagePosicaoDados.Config2, config2.ToArray()),
};
}
private List<byte[]> SensoresConfig(bool Conectar, bool ConfigurarTodos)
private List<(int, CanMessagePosicaoDados, byte[])> SensoresConfig(bool Conectar, bool ConfigurarTodos)
{
var config = new List<byte[]>();
var config = new List<(int, CanMessagePosicaoDados, byte[])>();
foreach (var sensor in Sensores.Where(x => (x.Aferir && (ConfigurarTodos ? true : x.Inicializado != Conectar)) || (!x.Aferir && x.Inicializado)))
{
@ -496,19 +500,19 @@ namespace AgroBase.Models.Modules
{
Conectar = false;
}
byte[] payload = sensor.ProtocoloConfiguracao(Pinout, Conectar, Dispositivo);
(CanMessagePosicaoDados posicao, byte[] payload) = sensor.ProtocoloConfiguracao(Pinout, Conectar, Dispositivo);
if (payload != null)
{
config.Add(payload);
config.Add((sensor.ID_Num, posicao, payload));
}
}
return config;
}
private List<byte[]> BicosConfig(bool Conectar, bool ConfigurarTodos)
private List<(int, CanMessagePosicaoDados, byte[])> BicosConfig(bool Conectar, bool ConfigurarTodos)
{
var config = new List<byte[]>();
var config = new List<(int, CanMessagePosicaoDados, byte[])>();
foreach (var bico in BicosPulverizadores.Where(x => (x.Comandar && (ConfigurarTodos ? true : x.Inicializado != Conectar)) || (!x.Comandar && x.Inicializado)))
{
@ -516,19 +520,19 @@ namespace AgroBase.Models.Modules
{
Conectar = false;
}
var payload = bico.ProtocoloConfiguracao(Pinout, Conectar);
(CanMessagePosicaoDados posicao, var payload) = bico.ProtocoloConfiguracao(Pinout, Conectar);
if (payload != null)
{
config.Add(payload);
config.Add((bico.ID_Num, posicao, payload));
}
}
return config;
}
private List<byte[]> BombasConfig(bool Conectar, bool ConfigurarTodos)
private List<(int, CanMessagePosicaoDados, byte[])> BombasConfig(bool Conectar, bool ConfigurarTodos)
{
var config = new List<byte[]>();
var config = new List<(int, CanMessagePosicaoDados, byte[])>();
foreach (var bomba in BombasPressurizadoras.Where(x => (x.Comandar && (ConfigurarTodos ? true : x.Inicializado != Conectar)) || (!x.Comandar && x.Inicializado)))
{
@ -536,10 +540,10 @@ namespace AgroBase.Models.Modules
{
Conectar = false;
}
var payload = bomba.ProtocoloConfiguracao(Pinout, Conectar);
if (payload != null)
List<(CanMessagePosicaoDados, byte[])> dados = bomba.ProtocoloConfiguracao(Pinout, Conectar);
foreach (var dado in dados)
{
config.AddRange(payload);
config.Add((bomba.ID_Num, dado.Item1, dado.Item2));
}
}
@ -589,7 +593,7 @@ namespace AgroBase.Models.Modules
{
if (RequisitarDados)
{
RequisitarDadosModulo(F_Code.ReqTx, false);
RequisitarDadosModulo(Variaveis.ID_Num_sTOD, CanMessagePosicaoDados.DadosAll, CanMessagePosicaoDados.DadosAll, true);
}
VerificaControleLeitura();
@ -740,30 +744,29 @@ namespace AgroBase.Models.Modules
}
public byte[] ProtocoloConfiguracao(PinoutDataModel pinout, bool conectar)
public (CanMessagePosicaoDados, byte[]) ProtocoloConfiguracao(PinoutDataModel pinout, bool conectar)
{
var pino = pinout.Pinos.FirstOrDefault(p => p.ComponenteID == ID);
return new byte[]
var data = new byte[]
{
(byte)ID_Num,
(byte)CanMessagePosicaoDados.Config1,
(byte)Componente,
(byte)(conectar ? 1 : 0),
(byte)(AtuacaoNivelAlto ? 1 : 0),
(byte)(pino?.Barramento ?? TiposBarramentos.CONTROLADOR),
(byte)(pino?.Pino ?? PinoutUtils.PINO_INVALIDO)
};
return (CanMessagePosicaoDados.Config1, data);
}
public (F_Code, byte[]) ProtocoloComando()
public (int, CanMessagePosicaoDados, byte[]) ProtocoloComando()
{
return (
F_Code.CmdTx,
ID_Num,
CanMessagePosicaoDados.Command1,
new byte[]
{
(byte)ID_Num,
(byte)CanMessagePosicaoDados.Command1,
(byte)(ComandoAtuar ? Estado.Ligado : Estado.Desligado)
}
);
@ -885,12 +888,10 @@ namespace AgroBase.Models.Modules
public List<byte[]> ProtocoloConfiguracao(PinoutDataModel pinout, bool conectar)
public List<(CanMessagePosicaoDados, byte[])> ProtocoloConfiguracao(PinoutDataModel pinout, bool conectar)
{
List<byte> config1 = new List<byte>()
{
(byte)ID_Num,
(byte)CanMessagePosicaoDados.Config1,
(byte)Componente,
(byte)(conectar ? 1 : 0),
(byte)Variaveis.OperacaoEmAndamento.Controle.PressaoLinha,
@ -900,39 +901,26 @@ namespace AgroBase.Models.Modules
List<byte> config2 = new List<byte>()
{
(byte)ID_Num,
(byte)CanMessagePosicaoDados.Config2,
(byte)Componente,
(byte)(pinout.Pinos.FirstOrDefault(x => x.Funcao == FuncoesPinout.INA)?.Pino ?? PinoutUtils.PINO_INVALIDO),
(byte)(pinout.Pinos.FirstOrDefault(x => x.Funcao == FuncoesPinout.INB)?.Pino ?? PinoutUtils.PINO_INVALIDO),
(byte)(pinout.Pinos.FirstOrDefault(x => x.Funcao == FuncoesPinout.PWM)?.Pino ?? PinoutUtils.PINO_INVALIDO),
};
if (conectar)
return new List<(CanMessagePosicaoDados, byte[])>()
{
return new List<byte[]>()
{
config1.ToArray(),
config2.ToArray()
(CanMessagePosicaoDados.Config1, config1.ToArray()),
(CanMessagePosicaoDados.Config2, config2.ToArray()),
};
}
else
{
return new List<byte[]>()
{
config1.ToArray()
};
}
}
public (F_Code, byte[]) ProtocoloComando()
public (int, CanMessagePosicaoDados, byte[]) ProtocoloComando()
{
return (
F_Code.CmdTx,
ID_Num,
CanMessagePosicaoDados.Command1,
new byte[]
{
(byte)ID_Num,
(byte)CanMessagePosicaoDados.Command1,
(byte)(ComandoAtuar ? Estado.Ligado : Estado.Desligado),
(byte)(Variaveis.OperacaoEmAndamento.Controle.PressaoLinha)
}
@ -1378,9 +1366,8 @@ namespace AgroBase.Models.Modules
public void ProcessarMensagem(CanMessage mensagem)
{
byte ID_Num = mensagem.DataRx[0];
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)mensagem.DataRx[1];
byte id = mensagem.IdTx;
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)mensagem.DataRx[0];
byte ID_Num = mensagem.DataRx[1];
var data = mensagem.DataRx;
var item = Variaveis.OperacaoEmAndamento.DispAtu.Dados.DadosLeitura;

View File

@ -12,19 +12,13 @@ namespace AgroBase.Models.Modules
public string ID { get; set; } = T_Code.Dir.ToString();
// SETs
public string Endereco { get; set; }
public byte EnderecoByte
{
get
{
return Convert.ToByte(Endereco.Replace("0x", ""), 16);
}
}
public byte _EnderecoCAN_Tx { get; set; }
public byte _EnderecoCAN_Rx { get; set; }
public string Mod_ID
{
get
{
return Variaveis.OperacaoEmAndamento.DispMvd?.Dados?.Modulos?.FirstOrDefault(x => x.DirMotor.EnderecoByte == EnderecoByte)?.Modulo_ID ?? "";
return Variaveis.OperacaoEmAndamento.DispMvd?.Dados?.Modulos?.FirstOrDefault(x => x.DirMotor._EnderecoCAN_Tx == _EnderecoCAN_Tx)?.Modulo_ID ?? "";
}
}
public Sentido Sentido_SP { get; set; } = Sentido.Parado;
@ -107,7 +101,7 @@ namespace AgroBase.Models.Modules
{
get
{
_leitura = MKS057DCanService.DadosLeitura?.FirstOrDefault(x => x.Endereco == EnderecoByte);
_leitura = MKS057DCanService.DadosLeitura?.FirstOrDefault(x => x.EnderecoTx == _EnderecoCAN_Tx);
return _leitura;
}
set
@ -174,12 +168,13 @@ namespace AgroBase.Models.Modules
public List<FuncoesPinout> Funcoes { get; set; }
public static DirecionalModel CarregarParametrosIniciais(string Mod_ID, string _Endereco)
public static DirecionalModel CarregarParametrosIniciais(string Mod_ID, byte _EnderecoTx, byte _EnderecoRx)
{
return new DirecionalModel()
{
ID = T_Code.Dir.ToString(),
Endereco = _Endereco,
_EnderecoCAN_Tx = _EnderecoTx,
_EnderecoCAN_Rx = _EnderecoRx,
Funcoes = new List<FuncoesPinout>()
{
FuncoesPinout.PUL,
@ -320,7 +315,7 @@ namespace AgroBase.Models.Modules
}
//MKS057DService.AdicionarComandoNaFila(MKS057DService.MontarComandoMovimento(EnderecoByte, Angulo_SP, Velocidade, Sentido_SP));
MKS057DCanService.Movimento(EnderecoByte, Angulo_SP, Velocidade, Sentido_SP);
MKS057DCanService.Movimento(_EnderecoCAN_Tx, _EnderecoCAN_Rx, Angulo_SP, Velocidade, Sentido_SP);
UltimoComandoEnviado = DateTime.Now;
}
@ -353,7 +348,7 @@ namespace AgroBase.Models.Modules
//await MKS057DService.EnviarComandoControle(MKS057DService.MontarComandoMovimento(Addr, _angulo, VelocidadeGiro, _sentido));
if (_anguloSP != _anguloSpAnterior)
{
MKS057DCanService.Movimento(EnderecoByte, _anguloSP, VelocidadeGiro, _sentido);
MKS057DCanService.Movimento(_EnderecoCAN_Tx, _EnderecoCAN_Rx, _anguloSP, VelocidadeGiro, _sentido);
_anguloSpAnterior = _anguloSP;
}
@ -420,7 +415,7 @@ namespace AgroBase.Models.Modules
private async Task SetZero()
{
MKS057DCanService.SetZero(EnderecoByte);
MKS057DCanService.SetZero(_EnderecoCAN_Tx, _EnderecoCAN_Rx);
for (int i = 0; i < 5; i++)
{
@ -433,11 +428,11 @@ namespace AgroBase.Models.Modules
}
else
{
MKS057DCanService.SetZero(EnderecoByte);
MKS057DCanService.SetZero(_EnderecoCAN_Tx, _EnderecoCAN_Rx);
}
}
MKS057DCanService.Movimento(EnderecoByte, 0, 10, Sentido.Parado);
MKS057DCanService.Movimento(_EnderecoCAN_Tx, _EnderecoCAN_Rx, 0, 10, Sentido.Parado);
Console.WriteLine($"Comando Angulo Zero: {Angulo}");
}

View File

@ -1,4 +1,5 @@
using System.Collections.Generic;
using AgroBase.Services;
using System.Collections.Generic;
namespace AgroBase.Models
{
@ -6,8 +7,9 @@ namespace AgroBase.Models
{
bool Conectado { get; }
int _TaxaAmostragem { get; set; }
byte _EnderecoCAN { get; set; }
List<byte[]> ProtocoloConfiguracao(bool Conectar);
byte _EnderecoCAN_Tx { get; set; }
byte _EnderecoCAN_Rx { get; set; }
List<(int, CanMessagePosicaoDados, byte[])> ProtocoloConfiguracao(bool Conectar);
void IniciarRegistrador();
void PararRegistrador();
void LimparDados<T>(T Dados);

View File

@ -1,8 +1,10 @@
using AgroBase.Services;
using System;
using System.Collections.Generic;
using System.Data.Odbc;
using System.Linq;
using static AgroBase.Models.Enums;
using static AgroBase.Services.OIDCanService.OidHandler;
namespace AgroBase.Models.Modules
{
@ -11,19 +13,14 @@ namespace AgroBase.Models.Modules
public string ID { get; set; } = T_Code.Mov.ToString();
// SETs
public string Endereco { get; set; }
public byte EnderecoByte
{
get
{
return Convert.ToByte(Endereco.Replace("0x", ""), 16);
}
}
public byte _EnderecoCAN_Tx { get; set; }
public byte _EnderecoCAN_Rx { get; set; }
public int heartBeatValue { get; set; } = 0;
public string Mod_ID
{
get
{
return Variaveis.OperacaoEmAndamento.DispMvd?.Dados?.Modulos?.FirstOrDefault(x => x.MovMotor.EnderecoByte == EnderecoByte)?.Modulo_ID ?? "";
return Variaveis.OperacaoEmAndamento.DispMvd?.Dados?.Modulos?.FirstOrDefault(x => x.MovMotor._EnderecoCAN_Tx == _EnderecoCAN_Tx)?.Modulo_ID ?? "";
}
}
public bool LeituraLigado
@ -35,7 +32,7 @@ namespace AgroBase.Models.Modules
}
public bool ComandoLigado { get; set; } = false;
//public bool Freio { get; set; } = false;
public int CodigoAlarme
public OidCodigoErro CodigoAlarme
{
get
{
@ -46,7 +43,7 @@ namespace AgroBase.Models.Modules
{
get
{
return CodigoAlarme > 0 && CodigoAlarme < 99;
return CodigoAlarme != OidCodigoErro.NenhumErro;
}
}
public int RPM_SP { get; set; } = 0;
@ -185,7 +182,7 @@ namespace AgroBase.Models.Modules
{
get
{
_leitura = OIDService.DadosLeitura?.FirstOrDefault(x => x.Endereco == EnderecoByte);
_leitura = OIDCanService.DadosLeitura?.FirstOrDefault(x => x.EnderecoTx == _EnderecoCAN_Tx);
return _leitura;
}
set
@ -253,12 +250,13 @@ namespace AgroBase.Models.Modules
public MvdServoFreioModel ConfigFreio { get; set; } = new MvdServoFreioModel();
public static MovimentacaoModel CarregarParametrosIniciais(string Mod_ID, string _Endereco)
public static MovimentacaoModel CarregarParametrosIniciais(string Mod_ID, byte _EnderecoTx, byte _EnderecoRx)
{
return new MovimentacaoModel()
{
ID = T_Code.Mov.ToString(),
Endereco = _Endereco,
_EnderecoCAN_Tx = _EnderecoTx,
_EnderecoCAN_Rx = _EnderecoRx,
Funcoes = new List<FuncoesPinout>()
{
FuncoesPinout.TMP,
@ -359,28 +357,16 @@ namespace AgroBase.Models.Modules
if ((Comandar && Inicializado) || simulando)
{
var _Controle = Variaveis.OperacaoEmAndamento.Controle;
if (AlarmeSensores || AlarmeMotor)
{
DirecaoAtual = Direcao.Parado;
Freado = false;
(AtuarServo, AnguloFreio) = ConfigFreio.AtualizarDadosFreio(Freado, 0, -1, 5);
if (AlarmeMotor)
{
OIDService.RegisrarErrosComunicacao(EnderecoByte, $"Módulo com código de alarme {CodigoAlarme}, reiniciando o módulo...");
OIDService.AdicionarComandoNaFila(new OIDComandoModel()
{
Endereco = EnderecoByte,
AguardaResposta = true,
TimeoutResposta = 500,
Get = false,
Parametro = OIDService.Parametros.First(x => x.Chave == "CodErro"),
Valor = 0
});
}
}
RPM_SP_Controle = Variaveis.OperacaoEmAndamento.Controle.RPM_Motor;
RPM_SP_Controle = _Controle.RPM_Motor;
RPM_SP =
DirecaoAtual == Direcao.Parado || Freado ? 0 :
RPM_SP_Controle;
@ -394,10 +380,10 @@ namespace AgroBase.Models.Modules
switch (DirecaoAtual)
{
case Direcao.Frente:
Sentido_SP = ConfigSentidos[Variaveis.OperacaoEmAndamento.Controle.TipoMovimento].Frente;
Sentido_SP = ConfigSentidos[_Controle.TipoMovimento].Frente;
break;
case Direcao.Tras:
Sentido_SP = ConfigSentidos[Variaveis.OperacaoEmAndamento.Controle.TipoMovimento].Tras;
Sentido_SP = ConfigSentidos[_Controle.TipoMovimento].Tras;
break;
default:
Sentido_SP = Sentido.Parado;
@ -409,32 +395,19 @@ namespace AgroBase.Models.Modules
return;
}
byte Addr = EnderecoByte;
byte Addr = _EnderecoCAN_Tx;
DateTime Agora = DateTime.Now;
bool SentidoAlterado = Sentido_SP != Sentido.Parado && (Leitura == null || Leitura.Direcao != Sentido_SP);
bool RPMAlterado = ComandoLigado && (Leitura == null || Leitura.ControleVelocidade != RPM_SP_Controle);
bool RPMAlterado = ComandoLigado && (Leitura == null || _Controle.PercentualVelocidadeSP != Variaveis.OperacaoEmAndamento.ControleAnterior.PercentualVelocidadeSP);
bool LigadoAlterado = Leitura == null || ComandoLigado != LeituraLigado;
bool FreioAlterado = Leitura == null || Leitura.Freado != Freado;
bool EnviaComando = SentidoAlterado || RPMAlterado || LigadoAlterado;
OIDModoControle modoControle =
Freado ? OIDModoControle.Freio :
ComandoLigado ? OIDModoControle.Velocidade :
OIDModoControle.Corrente;
if ((Leitura?.ModoControle ?? OIDModoControle.Velocidade) != modoControle)
{
OIDService.AdicionarComandoNaFila(new OIDComandoModel()
{
Endereco = Addr,
Parametro = OIDService.Parametros.First(x => x.Chave == "ModoControle"),
Valor = (int)modoControle,
Get = false,
AguardaResposta = false,
TimeoutResposta = 50,
});
}
OidFuncCode modoControle =
Freado ? OidFuncCode.ComandoCorrenteFreio :
ComandoLigado ? OidFuncCode.ComandoVelocidade :
OidFuncCode.ComandoCorrente;
if (EnviaComando && !Freado)
{
@ -444,23 +417,13 @@ namespace AgroBase.Models.Modules
0;
float velocidade = RPM_SP * mx;
string regisro = modoControle == OIDModoControle.Velocidade ? "ControleVelocidade" : "ControleCorrente";
OIDService.AdicionarComandoNaFila(new OIDComandoModel()
{
Endereco = Addr,
Parametro = OIDService.Parametros.First(x => x.Chave == regisro),
Valor = velocidade,
Get = false,
AguardaResposta = false,
TimeoutResposta = 50,
});
OIDCanService.ComandoControle(_EnderecoCAN_Tx, _EnderecoCAN_Rx, modoControle, velocidade);
}
}
if (AtuarServo)
{
string Mod_ID = Variaveis.OperacaoEmAndamento.DispMvd.Dados.Modulos.FirstOrDefault(x => x.MovMotor.Endereco == Endereco)?.Modulo_ID ?? "";
string Mod_ID = Variaveis.OperacaoEmAndamento.DispMvd.Dados.Modulos.FirstOrDefault(x => x.MovMotor._EnderecoCAN_Tx == _EnderecoCAN_Tx)?.Modulo_ID ?? "";
var ServoFreio = Variaveis.OperacaoEmAndamento.DispSen.Dados.Servos.FirstOrDefault(x => x.ID.Contains(Mod_ID) && x.Inicializado && x.Controlar);
if (ServoFreio != null)
{

View File

@ -11,7 +11,8 @@ namespace AgroBase.Models.Modules
public class MovimentacaoUnificadaModel : DispositivoBaseModel
{
public T_Code Dispositivo { get; set; } = T_Code.Mvd;
public byte _EnderecoCAN { get; set; } = 0x00;
public byte _EnderecoCAN_Tx { get; set; } = 0x00;
public byte _EnderecoCAN_Rx { get; set; } = 0x00;
public bool Conectado
{
@ -96,26 +97,26 @@ namespace AgroBase.Models.Modules
new ModuloMvdModel()
{
Modulo_ID = "ET",
MovMotor = MovimentacaoModel.CarregarParametrosIniciais("ET", "0x01"),
DirMotor = DirecionalModel.CarregarParametrosIniciais("ET", "0x01"),
MovMotor = MovimentacaoModel.CarregarParametrosIniciais("ET", 0x05, 0x05),
DirMotor = DirecionalModel.CarregarParametrosIniciais("ET", 0x01, 0x01),
},
new ModuloMvdModel()
{
Modulo_ID = "EF",
MovMotor = MovimentacaoModel.CarregarParametrosIniciais("EF", "0x03"),
DirMotor = DirecionalModel.CarregarParametrosIniciais("EF", "0x03")
MovMotor = MovimentacaoModel.CarregarParametrosIniciais("EF", 0x07, 0x07),
DirMotor = DirecionalModel.CarregarParametrosIniciais("EF", 0x03, 0x03)
},
new ModuloMvdModel()
{
Modulo_ID = "DT",
MovMotor = MovimentacaoModel.CarregarParametrosIniciais("DT", "0x02"),
DirMotor = DirecionalModel.CarregarParametrosIniciais("DT", "0x02")
MovMotor = MovimentacaoModel.CarregarParametrosIniciais("DT", 0x06, 0x06),
DirMotor = DirecionalModel.CarregarParametrosIniciais("DT", 0x02, 0x02)
},
new ModuloMvdModel()
{
Modulo_ID = "DF",
MovMotor = MovimentacaoModel.CarregarParametrosIniciais("DF", "0x04"),
DirMotor = DirecionalModel.CarregarParametrosIniciais("DF", "0x04")
MovMotor = MovimentacaoModel.CarregarParametrosIniciais("DF", 0x08, 0x08),
DirMotor = DirecionalModel.CarregarParametrosIniciais("DF", 0x04, 0x04)
},
},
};
@ -154,9 +155,9 @@ namespace AgroBase.Models.Modules
});
}
public List<byte[]> ProtocoloConfiguracao(bool Conectar)
public List<(int, CanMessagePosicaoDados, byte[])> ProtocoloConfiguracao(bool Conectar)
{
return new List<byte[]>();
return new List<(int, CanMessagePosicaoDados, byte[])>();
}
public void RecebeProtocoloModulo(string Protocolo)
@ -205,7 +206,7 @@ namespace AgroBase.Models.Modules
tmrRegistrador = new AsyncTaskTimerModel("tmrRegistrador_" + T_Code.Mvd.ToString(), tmrRegistrador_Tick, _TaxaAmostragem);
tmrRegistrador.Start();
tmrRegistradorMOV = new AsyncTaskTimerModel("tmrRegistrador_" + T_Code.Mov.ToString(), tmrRegistradorMOV_Tick, OIDService.TaxaAmostragem);
tmrRegistradorMOV = new AsyncTaskTimerModel("tmrRegistrador_" + T_Code.Mov.ToString(), tmrRegistradorMOV_Tick, OIDCanService.TaxaAmostragem);
tmrRegistradorMOV.Start();
tmrRegistradorDIR = new AsyncTaskTimerModel("tmrRegistrador_" + T_Code.Dir.ToString(), tmrRegistradorDIR_Tick, MKS057DCanService.TaxaAmostragem);
@ -245,42 +246,32 @@ namespace AgroBase.Models.Modules
return;
}
if (!OIDService.Iniciado && SerialService.DispositivosMapeados.Any(x => x.Dispositivo == T_Code.Mov))
if (!OIDCanService.Iniciado && SerialService.DispositivosMapeados.Any(x => x.Dispositivo == T_Code.Mov))
{
await OIDService.InicializarEthernetService();
foreach (var Leitura in OIDService.DadosLeitura.Where(x => x.UltimoComandoRecebido.AddSeconds(10) < DateTime.Now))
foreach (var Leitura in OIDCanService.DadosLeitura.Where(x => x.UltimoComandoRecebido.AddSeconds(10) < DateTime.Now))
{
OIDService.AdicionarComandoNaFila(new OIDComandoModel()
{
Endereco = Leitura.Endereco,
Parametro = OIDService.Parametros.First(x => x.Chave == "CodErro"),
Get = true,
AguardaResposta = true
});
OIDCanService.RequisitarDado(_EnderecoCAN_Tx, _EnderecoCAN_Rx, OIDCanService.OidHandler.OidParametros.CodErro);
}
tmrRegistradorMOV.SetInterval(3000);
return;
}
foreach (var Modulo in Modulos.Where(x => x.MovMotor.Inicializado).OrderBy(x => x.MovMotor._EnderecoCAN_Tx))
{
byte addrTx = Modulo.MovMotor._EnderecoCAN_Tx;
byte addrRx = Modulo.MovMotor._EnderecoCAN_Rx;
OIDCanService.RequisitarDado(addrTx, addrRx, OIDCanService.OidHandler.OidParametros.VelocidadeAtual);
OIDCanService.RequisitarDado(addrTx, addrRx, OIDCanService.OidHandler.OidParametros.Potencia);
OIDCanService.RequisitarDado(addrTx, addrRx, OIDCanService.OidHandler.OidParametros.Temperatura);
OIDCanService.RequisitarDado(addrTx, addrRx, OIDCanService.OidHandler.OidParametros.CicloTrabalho);
OIDCanService.RequisitarDado(addrTx, addrRx, OIDCanService.OidHandler.OidParametros.CodErro);
OIDCanService.RequisitarDado(addrTx, addrRx, OIDCanService.OidHandler.OidParametros.CorrenteBarramento);
OIDCanService.RequisitarDado(addrTx, addrRx, OIDCanService.OidHandler.OidParametros.CorrenteMotor);
OIDCanService.RequisitarDado(addrTx, addrRx, OIDCanService.OidHandler.OidParametros.Tensao);
var Controle = Variaveis.OperacaoEmAndamento.Controle.TiposControle?.FirstOrDefault(x => x.Tipo == T_Code.Mov);
foreach (var Modulo in Modulos.Where(x => x.MovMotor.Inicializado).OrderBy(x => x.MovMotor.EnderecoByte))
{
foreach (var Parametro in OIDService.Parametros.Where(x => x.LeituraLoop))
{
var Comando = new OIDComandoModel()
{
Endereco = Modulo.MovMotor.EnderecoByte,
AguardaResposta = true,
Parametro = Parametro,
Get = true,
TimeoutResposta = 200
};
OIDService.AdicionarComandoNaFila(Comando);
}
if (Controle != null)
{
Modulo.MovMotor.EnviarComandoControle(Controle.UltimaDirecao);
@ -291,7 +282,7 @@ namespace AgroBase.Models.Modules
Variaveis.OperacaoEmAndamento.DispMvd.Dados.RegistrarLogMov(Modulo);
}
tmrRegistradorMOV.SetInterval(OIDService.TaxaAmostragem);
tmrRegistradorMOV.SetInterval(OIDCanService.TaxaAmostragem);
}
private async Task tmrRegistradorDIR_Tick()
@ -303,12 +294,9 @@ namespace AgroBase.Models.Modules
if (!MKS057DCanService.Iniciado && SerialService.DispositivosMapeados.Any(x => x.Dispositivo == T_Code.Dir))
{
//await MKS057DService.InicializarEthernetService();
foreach (var Leitura in MKS057DCanService.DadosLeitura.Where(x => x.UltimoComandoRecebido.AddSeconds(10) < DateTime.Now))
{
//MKS057DService.AdicionarComandoNaFila(MKS057DService.MontarComandoRequisicaoPulsos(Leitura.Endereco));
MKS057DCanService.RequisitarDado(Leitura.Endereco, MKS057DCanService.MksHandler.MksFuncCode.PulsosRecebidos);
MKS057DCanService.RequisitarDado(Leitura.EnderecoTx, Leitura.EnderecoRx, MKS057DCanService.MksHandler.MksFuncCode.PulsosRecebidos);
}
tmrRegistradorDIR.SetInterval(3000);
@ -317,11 +305,8 @@ namespace AgroBase.Models.Modules
foreach (var Modulo in Modulos.Where(x => x.DirMotor.Inicializado))
{
byte modAddr = Modulo.DirMotor.EnderecoByte;
//MKS057DService.AdicionarComandoNaFila(MKS057DService.MontarComandoRequisicaoPulsos(modAddr));
MKS057DCanService.RequisitarDado(modAddr, MKS057DCanService.MksHandler.MksFuncCode.PulsosRecebidos);
//MKS057DService.AdicionarComandoNaFila(MKS057DService.MontarComandoRequisicaoIO(modAddr));
MKS057DCanService.RequisitarDado(modAddr, MKS057DCanService.MksHandler.MksFuncCode.IO);
MKS057DCanService.RequisitarDado(Modulo.DirMotor._EnderecoCAN_Tx, Modulo.DirMotor._EnderecoCAN_Rx, MKS057DCanService.MksHandler.MksFuncCode.PulsosRecebidos);
MKS057DCanService.RequisitarDado(Modulo.DirMotor._EnderecoCAN_Tx, Modulo.DirMotor._EnderecoCAN_Rx, MKS057DCanService.MksHandler.MksFuncCode.IO);
// Verifica se o angulo de set point do motor em questao e diferente do angulo atual, e se for, reenvia o comando para garantir que o motor esteja coerente com o set point
if (!MKS057DCanService.Referenciando && (Modulo.DirMotor.UltimoComandoEnviado.AddMilliseconds(MKS057DCanService.TaxaAmostragem) < DateTime.Now) && !Modulo.DirMotor.AtingiuAnguloSP)

View File

@ -15,7 +15,8 @@ namespace AgroBase.Models.Modules
{
public T_Code Dispositivo { get; set; } = T_Code.Sen;
public string Modulo_ID { get; set; } = T_Code.Sen.ToString();
public byte _EnderecoCAN { get; set; } = 0x11;
public byte _EnderecoCAN_Tx { get; set; } = 0x11;
public byte _EnderecoCAN_Rx { get; set; } = 0x12;
public int _TaxaAmostragem { get; set; } = 1000;
public bool RequisitarDados { get; set; } = true;
public static int PingsConsiderarConexao { get; set; } = 5;
@ -70,7 +71,8 @@ namespace AgroBase.Models.Modules
{
var obj = new SensoriamentoModel()
{
_EnderecoCAN = 0x11,
_EnderecoCAN_Tx = 0x11,
_EnderecoCAN_Rx = 0x12,
_TaxaAmostragem = 1000,
RequisitarDados = true,
CameraID_Caminho = "",
@ -776,11 +778,11 @@ namespace AgroBase.Models.Modules
CanService.DefinirPortaCOM(porta);
}
CanService.RegistrarHandler((byte)((int)_EnderecoCAN + 1), _SenHandler);
CanService.RegistrarHandler(_EnderecoCAN_Rx, _SenHandler);
if (CanService.IsConnected)
{
RequisitarDadosModulo(F_Code.ChkTx, Variaveis.ID_Num_sMOD);
RequisitarDadosModulo(Variaveis.ID_Num_sMOD, CanMessagePosicaoDados.Status, CanMessagePosicaoDados.Status, true);
await Task.Delay(1000);
@ -818,15 +820,15 @@ namespace AgroBase.Models.Modules
}
}
public void RequisitarDadosModulo(F_Code f_code, int ID_Num, CanMessagePosicaoDados posicao = CanMessagePosicaoDados.Status, bool aguardaResposta = true)
public void RequisitarDadosModulo(int ID_Num, CanMessagePosicaoDados posicaoTx, CanMessagePosicaoDados posicaoRx, bool aguardaResposta)
{
Variaveis.OperacaoEmAndamento.DispSen?.AdicionarMensagemFila(f_code, new byte[] { (byte)ID_Num, (byte)posicao }, aguardaResposta);
Variaveis.OperacaoEmAndamento.DispSen?.AdicionarMensagemFila(ID_Num, posicaoTx, posicaoRx, null, aguardaResposta);
}
public List<byte[]> ProtocoloConfiguracao(bool Conectar)
public List<(int, CanMessagePosicaoDados, byte[])> ProtocoloConfiguracao(bool Conectar)
{
// Inicializar o dicionário
List<byte[]> config = new List<byte[]>();
List<(int, CanMessagePosicaoDados, byte[])> config = new List<(int, CanMessagePosicaoDados, byte[])>();
if (!DadosLeitura.Conectado)
{
@ -838,61 +840,52 @@ namespace AgroBase.Models.Modules
bool configurarTodos = !DadosLeitura.Conectado && Conectar;
// Adicionar configurações dos Sinaleiros
List<byte[]> sinaleirosConfig = SinaleirosConfig(Conectar, configurarTodos);
var sinaleirosConfig = SinaleirosConfig(Conectar, configurarTodos);
config.AddRange(sinaleirosConfig);
// Adicionar configurações dos Servos
List<byte[]> servosConfig = ServosConfig(Conectar, configurarTodos);
var servosConfig = ServosConfig(Conectar, configurarTodos);
config.AddRange(servosConfig);
// Adicionar configurações dos Reles
List<byte[]> relesConfig = RelesConfig(Conectar, configurarTodos);
var relesConfig = RelesConfig(Conectar, configurarTodos);
config.AddRange(relesConfig);
// Adicionar configurações dos Sensores que devem ser aferidos
List<byte[]> sensoresConfig = SensoresConfig(Conectar, configurarTodos);
var sensoresConfig = SensoresConfig(Conectar, configurarTodos);
config.AddRange(sensoresConfig);
// Adicionar configurações do LoRa
if (!loRaService.Conectado || !loRaService.Configurado || configurarTodos)
{
config.AddRange(loRaService.ProtocoloConfiguracao(Pinout, Conectar));
var loraConfig = loRaService.ProtocoloConfiguracao(Pinout, Conectar);
config.AddRange(loraConfig);
}
return config;
}
private List<byte[]> ModConfig(bool Conectar)
private List<(int, CanMessagePosicaoDados, byte[])> ModConfig(bool Conectar)
{
var config1 = new List<byte>
{
Variaveis.ID_Num_sMOD,
(byte)CanMessagePosicaoDados.Config1,
(byte)S_Code.sMOD,
(byte)(Conectar ? 1 : 0),
(byte)(_TaxaAmostragem / 10),
(byte)(RequisitarDados ? 1 : 0),
LoRaParametrosBase.address
};
var config2 = new List<byte>
{
Variaveis.ID_Num_sMOD,
(byte)CanMessagePosicaoDados.Config2,
(byte)S_Code.sMOD,
};
config2.AddRange(PinoutModel.PinoProtocolo(Pinout, Funcoes, false));
config1.AddRange(PinoutModel.PinoProtocolo(Pinout, Funcoes, false));
return new List<byte[]>
return new List<(int, CanMessagePosicaoDados, byte[])>()
{
config1.ToArray(),
config2.ToArray()
(Variaveis.ID_Num_sMOD, CanMessagePosicaoDados.Config1, config1.ToArray()),
};
}
public List<byte[]> SensoresConfig(bool Conectar, bool ConfigurarTodos)
public List<(int, CanMessagePosicaoDados, byte[])> SensoresConfig(bool Conectar, bool ConfigurarTodos)
{
var config = new List<byte[]>();
var config = new List<(int, CanMessagePosicaoDados, byte[])>();
foreach (var sensor in Sensores.Where(x => (x.Aferir && (ConfigurarTodos ? true : x.Inicializado != Conectar)) || (!x.Aferir && x.Inicializado)))
{
@ -900,35 +893,36 @@ namespace AgroBase.Models.Modules
{
Conectar = false;
}
byte[] payload = sensor.ProtocoloConfiguracao(Pinout, Conectar, Dispositivo);
(CanMessagePosicaoDados posicao, byte[] payload) = sensor.ProtocoloConfiguracao(Pinout, Conectar, Dispositivo);
if (payload != null)
{
config.Add(payload);
config.Add((sensor.ID_Num, posicao, payload));
}
}
return config;
}
private List<byte[]> SinaleirosConfig(bool Conectar, bool ConfigurarTodos)
private List<(int, CanMessagePosicaoDados, byte[])> SinaleirosConfig(bool Conectar, bool ConfigurarTodos)
{
var config = new List<byte[]>();
var config = new List<(int, CanMessagePosicaoDados, byte[])>();
foreach (var sinaleiro in Sinaleiros.Where(x => (ConfigurarTodos ? true : x.Inicializado != Conectar)))
{
var payload = sinaleiro.ProtocoloConfiguracao(Pinout, Conectar);
(CanMessagePosicaoDados posicao, var payload) = sinaleiro.ProtocoloConfiguracao(Pinout, Conectar);
if (payload != null)
{
config.Add(payload);
config.Add((sinaleiro.ID_Num, posicao, payload));
}
}
return config;
}
private List<byte[]> RelesConfig(bool Conectar, bool ConfigurarTodos)
private List<(int, CanMessagePosicaoDados, byte[])> RelesConfig(bool Conectar, bool ConfigurarTodos)
{
var config = new List<byte[]>();
var config = new List<(int, CanMessagePosicaoDados, byte[])>();
foreach (var rele in Reles.Where(x => (x.Controlar && (ConfigurarTodos ? true : x.Inicializado != Conectar)) || (!x.Controlar && x.Inicializado)))
{
@ -936,19 +930,19 @@ namespace AgroBase.Models.Modules
{
Conectar = false;
}
var payload = rele.ProtocoloConfiguracao(Pinout, Conectar);
(CanMessagePosicaoDados posicao, var payload) = rele.ProtocoloConfiguracao(Pinout, Conectar);
if (payload != null)
{
config.Add(payload);
config.Add((rele.ID_Num, posicao, payload));
}
}
return config;
}
private List<byte[]> ServosConfig(bool Conectar, bool ConfigurarTodos)
private List<(int, CanMessagePosicaoDados, byte[])> ServosConfig(bool Conectar, bool ConfigurarTodos)
{
var config = new List<byte[]>();
var config = new List<(int, CanMessagePosicaoDados, byte[])>();
foreach (var servo in Servos.Where(x => (x.Controlar && (ConfigurarTodos ? true : x.Inicializado != Conectar)) || (!x.Controlar && x.Inicializado)))
{
@ -956,10 +950,10 @@ namespace AgroBase.Models.Modules
{
Conectar = false;
}
var payload = servo.ProtocoloConfiguracao(Pinout, Conectar);
(CanMessagePosicaoDados posicao, var payload) = servo.ProtocoloConfiguracao(Pinout, Conectar);
if (payload != null)
{
config.Add(payload);
config.Add((servo.ID_Num, posicao, payload));
}
}
@ -1009,7 +1003,7 @@ namespace AgroBase.Models.Modules
{
if (RequisitarDados)
{
RequisitarDadosModulo(F_Code.ReqTx, Variaveis.ID_Num_sTOD, CanMessagePosicaoDados.DadosAll, false);
RequisitarDadosModulo(Variaveis.ID_Num_sTOD, CanMessagePosicaoDados.DadosAll, CanMessagePosicaoDados.DadosAll, true);
}
VerificaControleLeitura();
@ -1181,12 +1175,10 @@ namespace AgroBase.Models.Modules
public List<SenSensorimanetoGrafico> LogGrafico = new List<SenSensorimanetoGrafico>();
public byte[] ProtocoloConfiguracao(PinoutDataModel Pinout, bool conectar, T_Code Dispositivo)
public (CanMessagePosicaoDados, byte[]) ProtocoloConfiguracao(PinoutDataModel Pinout, bool conectar, T_Code Dispositivo)
{
List<byte> config = new List<byte>
{
(byte)ID_Num,
(byte)CanMessagePosicaoDados.Config1,
(byte)Componente,
(byte)(conectar ? 1 : 0),
};
@ -1210,7 +1202,7 @@ namespace AgroBase.Models.Modules
}
}
return config.ToArray();
return (CanMessagePosicaoDados.Config1, config.ToArray());
}
@ -1260,35 +1252,31 @@ namespace AgroBase.Models.Modules
}
}
public byte[] ProtocoloConfiguracao(PinoutDataModel pinout, bool conectar)
public (CanMessagePosicaoDados, byte[]) ProtocoloConfiguracao(PinoutDataModel pinout, bool conectar)
{
var pino = pinout.Pinos.FirstOrDefault(p => p.ComponenteID == ID);
List<byte> config = new List<byte>
{
(byte)ID_Num,
(byte)CanMessagePosicaoDados.Config1,
(byte)Componente,
(byte)(conectar ? 1 : 0),
(byte)(pino?.Barramento ?? TiposBarramentos.CONTROLADOR),
(byte)(pino?.Pino ?? PinoutUtils.PINO_INVALIDO)
};
return config.ToArray();
return (CanMessagePosicaoDados.Config1, config.ToArray());
}
public (F_Code, byte[]) ProtocoloComando()
public (int, CanMessagePosicaoDados, byte[]) ProtocoloComando()
{
List<byte> frame = new List<byte>
{
(byte)ID_Num,
(byte)CanMessagePosicaoDados.Command1,
(byte)Comportamento.statusLED,
(byte)Comportamento.QtdPiscadas,
(byte)(Comportamento.TempoMs / 10),
(byte)(Comportamento.PausaMs / 10)
};
return (F_Code.CmdTx, frame.ToArray());
return (ID_Num, CanMessagePosicaoDados.Command1, frame.ToArray());
}
}
@ -1337,13 +1325,11 @@ namespace AgroBase.Models.Modules
}
}
public byte[] ProtocoloConfiguracao(PinoutDataModel pinout, bool conectar)
public (CanMessagePosicaoDados, byte[]) ProtocoloConfiguracao(PinoutDataModel pinout, bool conectar)
{
var pino = pinout.Pinos.FirstOrDefault(p => p.ComponenteID == ID);
List<byte> config = new List<byte>
{
(byte)ID_Num,
(byte)CanMessagePosicaoDados.Config1,
(byte)Componente,
(byte)(conectar ? 1 : 0),
(byte)(AtuacaoNivelAlto ? 1 : 0),
@ -1351,17 +1337,16 @@ namespace AgroBase.Models.Modules
(byte)(pino?.Pino ?? PinoutUtils.PINO_INVALIDO)
};
return config.ToArray();
return (CanMessagePosicaoDados.Config1, config.ToArray());
}
public (F_Code, byte[]) ProtocoloComando()
public (int, CanMessagePosicaoDados, byte[]) ProtocoloComando()
{
return (
F_Code.CmdTx,
ID_Num,
CanMessagePosicaoDados.Command1,
new byte[]
{
(byte)ID_Num,
(byte)CanMessagePosicaoDados.Command1,
(byte)StatusControle
}
);
@ -1408,14 +1393,12 @@ namespace AgroBase.Models.Modules
}
}
public byte[] ProtocoloConfiguracao(PinoutDataModel pinout, bool conectar)
public (CanMessagePosicaoDados, byte[]) ProtocoloConfiguracao(PinoutDataModel pinout, bool conectar)
{
var pino = pinout.Pinos.FirstOrDefault(p => p.ComponenteID == ID);
List<byte> config = new List<byte>
{
(byte)ID_Num,
(byte)CanMessagePosicaoDados.Config1,
(byte)Componente,
(byte)(conectar ? 1 : 0),
(byte)(Incremental ? 1 : 0),
@ -1423,17 +1406,16 @@ namespace AgroBase.Models.Modules
(byte)(pino?.Pino ?? PinoutUtils.PINO_INVALIDO)
};
return config.ToArray();
return (CanMessagePosicaoDados.Config1, config.ToArray());
}
public (F_Code, byte[]) ProtocoloComando()
public (int, CanMessagePosicaoDados, byte[]) ProtocoloComando()
{
return (
F_Code.CmdTx,
ID_Num,
CanMessagePosicaoDados.Command1,
new byte[]
{
(byte)ID_Num,
(byte)CanMessagePosicaoDados.Command1,
(byte)_AnguloControle
}
);
@ -2044,6 +2026,7 @@ namespace AgroBase.Models.Modules
private S_Code DetectarComponenteDoID_Num(int ID_Num)
{
if (ID_Num == Variaveis.ID_Num_sMOD) return S_Code.sMOD;
if (ID_Num == Variaveis.ID_Num_sTOD) return S_Code.sTOD;
if (ID_Num == Variaveis.ID_Num_sLRA) return S_Code.sLRA;
var Disp = Variaveis.OperacaoEmAndamento.DispSen.Dados;
@ -2330,9 +2313,8 @@ namespace AgroBase.Models.Modules
public void ProcessarMensagem(CanMessage mensagem)
{
byte ID_Num = mensagem.DataRx[0];
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)mensagem.DataRx[1];
byte id = mensagem.IdTx;
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)mensagem.DataRx[0];
byte ID_Num = mensagem.DataRx[1];
var data = mensagem.DataRx;
var item = Variaveis.OperacaoEmAndamento.DispSen.Dados.DadosLeitura;
@ -2380,6 +2362,17 @@ namespace AgroBase.Models.Modules
}
break;
}
case CanMessagePosicaoDados.DadosAll:
{
if (componente == S_Code.sTOD)
{
int latenciaLoop = data[2];
Variaveis.OperacaoEmAndamento.DispSen.Dados.DadosLeitura.LatenciaLoop = latenciaLoop;
Console.WriteLine($"[SEN] Ciclo concluido. Latencia de loop: {latenciaLoop} ms");
}
break;
}
case CanMessagePosicaoDados.Dados1:
{
switch (componente)

View File

@ -3,12 +3,14 @@ using System;
using System.Collections.Generic;
using System.Linq;
using static AgroBase.Models.Enums;
using static AgroBase.Services.OIDCanService.OidHandler;
namespace AgroBase.Models
{
public class OIDModel
public class OID485Model
{
public byte Endereco { get; set; }
public byte EnderecoTx { get; set; }
public byte EnderecoRx { get; set; }
public bool Iniciado
{
get
@ -30,84 +32,84 @@ namespace AgroBase.Models
{
get
{
return (OIDModoControle)ConvertByteArrayToInt(GetParametroValue(OIDService.Parametros.First(x => x.Chave == "ModoControle").Registro));
return (OIDModoControle)ConvertByteArrayToInt(GetParametroValue(OIDRs485Service.Parametros.First(x => x.Chave == "ModoControle").Registro));
}
}
public int ControleCorrente
{
get
{
return ConvertByteArrayToInt(GetParametroValue(OIDService.Parametros.First(x => x.Chave == "ControleCorrente").Registro));
return ConvertByteArrayToInt(GetParametroValue(OIDRs485Service.Parametros.First(x => x.Chave == "ControleCorrente").Registro));
}
}
public int ControleVelocidade
{
get
{
return ConvertByteArrayToInt(GetParametroValue(OIDService.Parametros.First(x => x.Chave == "ControleVelocidade").Registro));
return ConvertByteArrayToInt(GetParametroValue(OIDRs485Service.Parametros.First(x => x.Chave == "ControleVelocidade").Registro));
}
}
public int ControleCicloTrabalho
{
get
{
return ConvertByteArrayToInt(GetParametroValue(OIDService.Parametros.First(x => x.Chave == "ControleCicloTrabalho").Registro));
return ConvertByteArrayToInt(GetParametroValue(OIDRs485Service.Parametros.First(x => x.Chave == "ControleCicloTrabalho").Registro));
}
}
public int ControleCorrenteFreio
{
get
{
return ConvertByteArrayToInt(GetParametroValue(OIDService.Parametros.First(x => x.Chave == "ControleCorrenteFreio").Registro));
return ConvertByteArrayToInt(GetParametroValue(OIDRs485Service.Parametros.First(x => x.Chave == "ControleCorrenteFreio").Registro));
}
}
public int RampaSubidaVelocidade
{
get
{
return ConvertByteArrayToInt(GetParametroValue(OIDService.Parametros.First(x => x.Chave == "RampaSubidaVelocidade").Registro));
return ConvertByteArrayToInt(GetParametroValue(OIDRs485Service.Parametros.First(x => x.Chave == "RampaSubidaVelocidade").Registro));
}
}
public int RampaDescidaVelocidade
{
get
{
return ConvertByteArrayToInt(GetParametroValue(OIDService.Parametros.First(x => x.Chave == "RampaDescidaVelocidade").Registro));
return ConvertByteArrayToInt(GetParametroValue(OIDRs485Service.Parametros.First(x => x.Chave == "RampaDescidaVelocidade").Registro));
}
}
public int CodigoAlarme
{
get
{
return ConvertByteArrayToInt(GetParametroValue(OIDService.Parametros.First(x => x.Chave == "CodErro").Registro));
return ConvertByteArrayToInt(GetParametroValue(OIDRs485Service.Parametros.First(x => x.Chave == "CodErro").Registro));
}
}
public int Heartbeat
{
get
{
return ConvertByteArrayToInt(GetParametroValue(OIDService.Parametros.First(x => x.Chave == "Heartbeat").Registro));
return ConvertByteArrayToInt(GetParametroValue(OIDRs485Service.Parametros.First(x => x.Chave == "Heartbeat").Registro));
}
}
public double Torque_Max
{
get
{
return ConvertByteArrayToFloat(GetParametroValue(OIDService.Parametros.First(x => x.Chave == "CorrenteTorqueMaximo").Registro));
return ConvertByteArrayToFloat(GetParametroValue(OIDRs485Service.Parametros.First(x => x.Chave == "CorrenteTorqueMaximo").Registro));
}
}
public int ERPM
{
get
{
return ConvertByteArrayToInt(GetParametroValue(OIDService.Parametros.First(x => x.Chave == "VelocidadeAngular").Registro));
return ConvertByteArrayToInt(GetParametroValue(OIDRs485Service.Parametros.First(x => x.Chave == "VelocidadeAngular").Registro));
}
}
public double CorrenteMotor
{
get
{
var P_A = parametros.FirstOrDefault(x => x.Registro == OIDService.Parametros.First(y => y.Chave == "CorrenteMotor").Registro);
var P_A = parametros.FirstOrDefault(x => x.Registro == OIDRs485Service.Parametros.First(y => y.Chave == "CorrenteMotor").Registro);
if (P_A == null)
{
return -1;
@ -120,7 +122,7 @@ namespace AgroBase.Models
{
get
{
var P_A = parametros.FirstOrDefault(x => x.Registro == OIDService.Parametros.First(y => y.Chave == "CorrenteBarramento").Registro);
var P_A = parametros.FirstOrDefault(x => x.Registro == OIDRs485Service.Parametros.First(y => y.Chave == "CorrenteBarramento").Registro);
if (P_A == null)
{
return -1;
@ -143,7 +145,7 @@ namespace AgroBase.Models
{
get
{
var P_V = parametros.FirstOrDefault(x => x.Registro == OIDService.Parametros.First(y => y.Chave == "VelocidadeAngular").Registro);
var P_V = parametros.FirstOrDefault(x => x.Registro == OIDRs485Service.Parametros.First(y => y.Chave == "VelocidadeAngular").Registro);
if (P_V == null)
{
return 0;
@ -156,7 +158,7 @@ namespace AgroBase.Models
{
get
{
var P_V = parametros.FirstOrDefault(x => x.Registro == OIDService.Parametros.First(y => y.Chave == "Tensao").Registro);
var P_V = parametros.FirstOrDefault(x => x.Registro == OIDRs485Service.Parametros.First(y => y.Chave == "Tensao").Registro);
if (P_V == null)
{
return -1;
@ -169,7 +171,7 @@ namespace AgroBase.Models
{
get
{
var P_T = parametros.FirstOrDefault(x => x.Registro == OIDService.Parametros.First(y => y.Chave == "Temperatura").Registro);
var P_T = parametros.FirstOrDefault(x => x.Registro == OIDRs485Service.Parametros.First(y => y.Chave == "Temperatura").Registro);
if (P_T == null)
{
return -1;
@ -182,7 +184,7 @@ namespace AgroBase.Models
{
get
{
var P_W = parametros.FirstOrDefault(x => x.Registro == OIDService.Parametros.First(y => y.Chave == "Potencia").Registro);
var P_W = parametros.FirstOrDefault(x => x.Registro == OIDRs485Service.Parametros.First(y => y.Chave == "Potencia").Registro);
if (P_W == null)
{
return -1;
@ -195,7 +197,7 @@ namespace AgroBase.Models
{
get
{
var P_C = parametros.FirstOrDefault(x => x.Registro == OIDService.Parametros.First(y => y.Chave == "CicloTrabalho").Registro);
var P_C = parametros.FirstOrDefault(x => x.Registro == OIDRs485Service.Parametros.First(y => y.Chave == "CicloTrabalho").Registro);
if (P_C == null)
{
return -1;
@ -252,6 +254,69 @@ namespace AgroBase.Models
}
}
public class OIDModel
{
public byte EnderecoTx { get; set; }
public byte EnderecoRx { get; set; }
public bool Iniciado
{
get
{
// Houve comandos recebidos do driver dentro dos ultimos 10 segundos
bool iniciado = UltimoComandoRecebido.AddSeconds(10) > DateTime.Now;
if (!iniciado && Configurado)
{
Configurado = false;
}
return iniciado;
}
}
public bool Configurado { get; set; }
public DateTime UltimoComandoRecebido { get; set; }
public OIDModoControle ModoControle { get; set; }
public OidCodigoErro CodigoAlarme { get; set; }
public int ERPM { get; set; }
public double CorrenteMotor { get; set; }
public double CorrenteBarramento { get; set; }
public Sentido Direcao
{
get
{
return
ERPM > 0 ? Sentido.Horario :
ERPM < 0 ? Sentido.Antihorario :
Sentido.Parado;
}
}
public double RPM
{
get
{
double rpm = Math.Abs((double)ERPM / (double)VariaveisEquipamento.NumeroPolosMotor);
return rpm;
}
}
public double Tensao { get; set; }
public double Temperatura { get; set; }
public double Potencia { get; set; }
public double CicloTrabalho { get; set; }
public bool Freado
{
get
{
return ModoControle == OIDModoControle.Freio || ModoControle == OIDModoControle.FreioDeMao;
}
}
public double PosicaoAbsoluta { get; set; }
public double PosicaoRelativa { get; set; }
public double ModoCodificador { get; set; }
public double ErroHistorico { get; set; }
public double IO_Status { get; set; }
}
public class OIDParametrosRequisitar
{
public ushort Registro { get; set; }

View File

@ -15,6 +15,7 @@ using System.Drawing;
using System.Text;
using System.Windows.Forms.DataVisualization.Charting;
using CefSharp.WinForms;
using static AgroBase.Services.OIDCanService.OidHandler;
namespace AgroBase.Models
{
@ -3385,7 +3386,7 @@ namespace AgroBase.Models
public double Tensao { get; set; }
public double Potencia { get; set; }
public double CicloTrabalho { get; set; }
public int CodAlarme { get; set; }
public OidCodigoErro CodAlarme { get; set; }
public bool AlarmeSensores { get; set; }
public bool AlarmeComando { get; set; }
public bool EmFreio { get; set; }

View File

@ -1137,6 +1137,15 @@ namespace AgroBase.Models
return comando;
}
public static byte StringToHexByte(string _st)
{
return Convert.ToByte(_st.Replace("0x", ""), 16);
}
public static string HexByteToString(byte _bt)
{
return "0x" + _bt.ToString("X").PadLeft(2, '0');
}
}

View File

@ -253,7 +253,7 @@ namespace AgroBase.Services
byte Addr = 0;
try
{
Addr = Modulo.MovMotor.EnderecoByte;
Addr = Modulo.MovMotor._EnderecoCAN_Tx;
}
catch
{
@ -379,7 +379,7 @@ namespace AgroBase.Services
foreach (var Mod_ID in Mod_IDs)
{
var Modulo = Variaveis.OperacaoEmAndamento.DispMvd.Dados.Modulos.FirstOrDefault(x => x.Modulo_ID == Mod_ID);
byte Addr = Modulo.MovMotor.EnderecoByte;
byte Addr = Modulo.MovMotor._EnderecoCAN_Tx;
if (DadosLeitura.Any(x => x.Endereco == Addr && !x.Configurado))
{
@ -403,7 +403,7 @@ namespace AgroBase.Services
private static void ConfigurarDriver(byte Addr)
{
var Modulo = Variaveis.OperacaoEmAndamento.DispMvd.Dados.Modulos.FirstOrDefault(x => x.MovMotor.EnderecoByte == Addr);
var Modulo = Variaveis.OperacaoEmAndamento.DispMvd.Dados.Modulos.FirstOrDefault(x => x.MovMotor._EnderecoCAN_Tx == Addr);
AdicionarComandoNaFila(new BLDComandoModel()
{
Endereco = Addr,

View File

@ -71,16 +71,19 @@ namespace AgroBase.Services
}
private static AsyncTaskTimerModel tmrEnviarCAN;
private static AsyncTaskTimerModel tmrOuvirCAN;
private static AsyncTaskTimerModel tmrProcessarCAN;
private static StringBuilder SerialCANBuffer = new StringBuilder();
private static object _framesLock = new object();
private static readonly Queue<string> FramesRecebidos = new Queue<string>();
private static readonly ConcurrentDictionary<byte, ICanMessageHandler> _roteadores = new ConcurrentDictionary<byte, ICanMessageHandler>();
private static byte? _ultimoIdEnviado = null;
private static List<CanMessage> Mensagens = new List<CanMessage>();
public static void RegistrarHandler(byte endereco, ICanMessageHandler handler)
public static void RegistrarHandler(byte endereco_rx, ICanMessageHandler handler)
{
_roteadores[endereco] = handler;
_roteadores[endereco_rx] = handler;
}
public static void DefinirPortaCOM(SerialPort Porta)
@ -110,9 +113,13 @@ namespace AgroBase.Services
tmrOuvirCAN.Start();
tmrEnviarCAN?.Dispose();
tmrEnviarCAN = new AsyncTaskTimerModel("tmrEnviarCAN", EnviarCAN, 5);
tmrEnviarCAN = new AsyncTaskTimerModel("tmrEnviarCAN", EnviarCAN, 100);
tmrEnviarCAN.Start();
tmrProcessarCAN?.Dispose();
tmrProcessarCAN = new AsyncTaskTimerModel("tmrProcessarCAN", ProcessarCAN, 5);
tmrProcessarCAN.Start();
IsConnected = true;
}
}
@ -140,7 +147,10 @@ namespace AgroBase.Services
if (!string.IsNullOrWhiteSpace(frame))
{
ProcessarFrameCAN(frame);
lock (_framesLock)
{
FramesRecebidos.Enqueue(frame);
}
}
}
else
@ -151,6 +161,24 @@ namespace AgroBase.Services
}
}
private static async Task ProcessarCAN()
{
string frame = null;
lock (_framesLock)
{
if (FramesRecebidos.Count > 0)
{
frame = FramesRecebidos.Dequeue();
}
}
if (frame != null)
{
ProcessarFrameCAN(frame);
}
}
private static void ProcessarFrameCAN(string frame)
{
// Ex: t00183301020304
@ -169,12 +197,16 @@ namespace AgroBase.Services
data[i] = Convert.ToByte(frame.Substring(5 + i * 2, 2), 16);
}
byte funcCodeRx = data[0];
byte fCodeRx = data[0];
var mensagem = new CanMessage();
lock (Mensagens)
{
mensagem = Mensagens.Where(x => x.IdRx == id).OrderBy(x => x.EnviadoEm).FirstOrDefault(x => x.Enviado && !x.Respondido && x.funcCodeRx == funcCodeRx);
mensagem = Mensagens
.Where(x => x.IdRx == id)
.OrderBy(x => x.EnviadoEm)
.FirstOrDefault(x => x.Enviado && !x.Respondido && x.funcCodeRx == fCodeRx);
}
if (mensagem == null)
@ -192,7 +224,7 @@ namespace AgroBase.Services
}
else
{
Console.WriteLine($"[CAN] ID_Num não tratado: 0x{funcCodeRx:X2}");
Console.WriteLine($"[CAN] ID_Num não tratado: 0x{id:X2}, fCodeRx: 0x{fCodeRx:X2}");
}
}
catch (Exception ex)
@ -201,12 +233,12 @@ namespace AgroBase.Services
}
}
public static void AdicionarMensagemNaFila(T_Code Dispositivo, byte idTx, byte idRx, byte funcCode, byte[] payload = null, bool get = true, byte ID_Num = 0x00)
public static void AdicionarMensagemNaFila(T_Code Dispositivo, byte idTx, byte idRx, byte funcCodeTx, byte funcCodeRx, byte[] payload = null, bool get = true)
{
if (_PortaCAN?.IsOpen != true) return;
// Monta o payload com funcCode + dados + CRC
var dados = new List<byte> { funcCode };
var dados = new List<byte>() { funcCodeTx };
if (payload != null)
dados.AddRange(payload);
@ -220,10 +252,10 @@ namespace AgroBase.Services
{
Momento = DateTime.Now,
Dispositivo = Dispositivo,
funcCodeTx = funcCode,
IdTx = idTx,
IdRx = idRx,
funcCodeRx = ID_Num,
funcCodeTx = funcCodeTx,
funcCodeRx = funcCodeRx,
DataTx = dados.ToArray(),
ComResposta = get
};

View File

@ -19,13 +19,6 @@ namespace AgroBase.Comum
public T_Code Dispositivo { get; set; } = T_Code.Vzo;
public string _Nome { get; set; }
public string _Descricao { get; set; }
public byte _EnderecoCAN
{
get
{
return Dados._EnderecoCAN;
}
}
public int _TaxaAmostragem
{
get
@ -71,12 +64,17 @@ namespace AgroBase.Comum
VariaveisOperacao.RegistrarLogDispositivo(Logs, Dispositivo, ".json", 100);
}
public void AdicionarMensagemFila(F_Code funcao, byte[] dados = null, bool get = true, byte ID_Num = 0x00)
public void AdicionarMensagemFila(int ID_Num, CanMessagePosicaoDados PosicaoTx, CanMessagePosicaoDados PosicaoRx, byte[] dados = null, bool get = true)
{
if ((int)funcao % 2 == 1)
List<byte> payload = new List<byte>()
{
CanService.AdicionarMensagemNaFila(Dispositivo, _EnderecoCAN, (byte)((int)_EnderecoCAN + 1), (byte)funcao, dados, get, ID_Num);
(byte)ID_Num,
};
if (dados != null)
{
payload.AddRange(dados);
}
CanService.AdicionarMensagemNaFila(Dispositivo, Dados._EnderecoCAN_Tx, Dados._EnderecoCAN_Rx, (byte)PosicaoTx, (byte)PosicaoRx, payload.ToArray(), get);
}
public Control InstanciarDispositivo(int index)
@ -369,7 +367,7 @@ namespace AgroBase.Comum
}
var Config = Dados.ProtocoloConfiguracao(true);
frmInstancial.frmPrincipal.lblStripErro.Text = Config.Any() ? FuncoesGlobais.ConverterComandoBytesParaTexto(Config.First().ToArray()) : "";
//frmInstancial.frmPrincipal.lblStripErro.Text = Config.Any() ? FuncoesGlobais.ConverterComandoBytesParaTexto(Config.First().ToArray()) : "";
}
private void nudAmostragem_ValueChanged(object sender, EventArgs e)
@ -397,10 +395,10 @@ namespace AgroBase.Comum
public void EnviarProtocolosConfiguracao(bool Conectar = true)
{
var Config = Dados.ProtocoloConfiguracao(Conectar);
List<(int ID_Num, CanMessagePosicaoDados Posicao, byte[] dados)> Config = Dados.ProtocoloConfiguracao(Conectar);
foreach (var data in Config)
{
AdicionarMensagemFila(F_Code.CfgTx, data, false);
AdicionarMensagemFila(data.ID_Num, data.Posicao, CanMessagePosicaoDados.Status, data.dados, false);
}
}

View File

@ -9,13 +9,12 @@ namespace AgroBase.Services
T_Code Dispositivo { get; set; }
string _Nome { get; set; }
string _Descricao { get; set; }
byte _EnderecoCAN { get; }
DispositivoBaseModel Dados { get; set; }
GroupBox gpbItem { get; set; }
Control InstanciarDispositivo(int index);
void AtualizaIndex(int index);
void SalvarParametros(DispositivoBaseModel dados);
void AdicionarMensagemFila(F_Code funcao, byte[] dados, bool get, byte ID_Num);
void AdicionarMensagemFila(int ID_Num, CanMessagePosicaoDados PosicaoTx, CanMessagePosicaoDados PosicaoRx, byte[] dados = null, bool get = true);
void EnviarProtocolosConfiguracao(bool Conectar = true);
void CarregarParametrosModulos();
}

View File

@ -25,14 +25,9 @@ namespace AgroBase.Services
public LoRaParametrosModel Parametros { get; set; }
public List<FuncoesPinout> Funcoes { get; set; }
public List<byte[]> ProtocoloConfiguracao(PinoutDataModel Pinout, bool conectar)
public List<(int, CanMessagePosicaoDados, byte[])> ProtocoloConfiguracao(PinoutDataModel Pinout, bool conectar)
{
List<byte> config1 = new List<byte>
{
(byte)ID_Num,
(byte)CanMessagePosicaoDados.Config1,
};
List<byte> config1 = new List<byte>();
var _pinout = Pinout.Clone();
_pinout.Pinos = _pinout.Pinos.Where(x => x.ComponenteID == ID).ToList();
if (_pinout.Pinos.Count > 0)
@ -43,8 +38,6 @@ namespace AgroBase.Services
List<byte> config2 = new List<byte>
{
(byte)ID_Num,
(byte)CanMessagePosicaoDados.Config2,
Parametros.address,
Parametros.baudAndAirRate,
Parametros.packetSizeAndPower,
@ -52,14 +45,18 @@ namespace AgroBase.Services
Parametros.tranModeAndWorCycle
};
return new List<byte[]>() { config1.ToArray(), config2.ToArray() };
return new List<(int, CanMessagePosicaoDados, byte[])>()
{
(ID_Num, CanMessagePosicaoDados.Config1, config1.ToArray()),
(ID_Num, CanMessagePosicaoDados.Config2, config2.ToArray()),
};
}
public async Task<(bool, LoRaParametrosModel)> RequisitarParametrosModulo()
{
DateTime inicio = DateTime.Now;
bool sucesso = false;
Variaveis.OperacaoEmAndamento.DispSen?.Dados?.RequisitarDadosModulo(F_Code.CmdTx, Variaveis.ID_Num_sLRA, CanMessagePosicaoDados.Command1);
Variaveis.OperacaoEmAndamento.DispSen?.Dados?.RequisitarDadosModulo(Variaveis.ID_Num_sLRA, CanMessagePosicaoDados.Command1, CanMessagePosicaoDados.Dados1, true);
while (!sucesso && inicio.AddMilliseconds(2000) > DateTime.Now)
{
await Task.Delay(10);
@ -98,14 +95,7 @@ namespace AgroBase.Services
if (payload.Length > 5) return false; // Payload muito grande para o nosso protocolo CAN-Style LoRa
List<byte> dados = new List<byte>
{
(byte)ID_Num,
(byte)posicao
};
dados.AddRange(payload);
Variaveis.OperacaoEmAndamento.DispSen?.AdicionarMensagemFila(F_Code.CmdTx, dados.ToArray(), false);
Variaveis.OperacaoEmAndamento.DispSen?.AdicionarMensagemFila(ID_Num, posicao, posicao, payload, false);
return true;
}

View File

@ -53,15 +53,14 @@ namespace AgroBase.Services
// Verifica e inicializa cada módulo conectado
foreach (var Modulo in Variaveis.OperacaoEmAndamento.DispMvd.Dados.Modulos.Where(x => !x.DirMotor.Inicializado))
{
byte Addr = Modulo.DirMotor.EnderecoByte;
CanService.RegistrarHandler(Addr, _MksHandler);
CanService.RegistrarHandler(Modulo.DirMotor._EnderecoCAN_Rx, _MksHandler);
// Envia comando relevante para verificar o dispositivo
RequisitarDado(Addr, MksFuncCode.Versao);
RequisitarDado(Modulo.DirMotor._EnderecoCAN_Tx, Modulo.DirMotor._EnderecoCAN_Rx, MksFuncCode.Versao);
await Task.Delay(1000);
if (DadosLeitura.Any(x => x.Endereco == Addr && x.Iniciado))
if (DadosLeitura.Any(x => x.EnderecoRx == Modulo.DirMotor._EnderecoCAN_Rx && x.Iniciado))
{
Mod_IDs.Add(Modulo.Modulo_ID);
}
@ -91,11 +90,10 @@ namespace AgroBase.Services
foreach (var Mod_ID in Mod_IDs)
{
var Modulo = Variaveis.OperacaoEmAndamento.DispMvd.Dados.Modulos.FirstOrDefault(x => x.Modulo_ID == Mod_ID);
byte Addr = Modulo.DirMotor.EnderecoByte;
if (!SerialService.DispositivosMapeados.Any(x => x.Dispositivo == T_Code.Dir && x.Mod_ID == Mod_ID))
{
var Leitura = DadosLeitura.FirstOrDefault(x => x.Endereco == Addr);
var Leitura = DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Modulo.DirMotor._EnderecoCAN_Tx);
if (Leitura != null)
{
SerialService.DispositivosMapeados.Add(new DispositivoDetalhesModel()
@ -136,37 +134,37 @@ namespace AgroBase.Services
#region COMANDOS
private static void EnviarComando(T_Code Dispositivo, byte id, byte funcCode, byte[] payload = null, bool get = true)
private static void EnviarComando(T_Code Dispositivo, byte idTx, byte idRx, byte funcCode, byte[] payload = null, bool get = true)
{
CanService.AdicionarMensagemNaFila(Dispositivo, id, id, funcCode, payload, get, funcCode);
CanService.AdicionarMensagemNaFila(Dispositivo, idTx, idRx, funcCode, funcCode, payload, get);
}
public static void SetModoOperacao(byte id, byte modo)
public static void SetModoOperacao(byte idTx, byte idRx, byte modo)
{
EnviarComando(Dispositivo, id, 0x82, new byte[] { modo }, false);
EnviarComando(Dispositivo, idTx, idRx, 0x82, new byte[] { modo }, false);
}
public static void RequisitarDado(byte id, MksFuncCode dado)
public static void RequisitarDado(byte idTx, byte idRx, MksFuncCode dado)
{
EnviarComando(Dispositivo, id, (byte)dado);
EnviarComando(Dispositivo, idTx, idRx, (byte)dado);
}
public static void SetZero(byte id)
public static void SetZero(byte idTx, byte idRx)
{
EnviarComando(Dispositivo, id, (byte)MksFuncCode.SetZero, null, false);
EnviarComando(Dispositivo, idTx, idRx, (byte)MksFuncCode.SetZero, null, false);
}
public static void Parar(byte id, ModosControle modo = ModosControle.AnguloAbsoluto)
public static void Parar(byte idTx, byte idRx, ModosControle modo = ModosControle.AnguloAbsoluto)
{
byte funcCode =
modo == ModosControle.Pulsos ? (byte)MksFuncCode.ModoControlePulsos :
modo == ModosControle.AnguloRelativo ? (byte)MksFuncCode.ModoControleAnguloRelativo :
(byte)MksFuncCode.ModoControleAnguloAbsoluto;
EnviarComando(Dispositivo, id, funcCode, new byte[] { 0x00 }, false);
EnviarComando(Dispositivo, idTx, idRx, funcCode, new byte[] { 0x00 }, false);
}
public static void Movimento(byte id, double angulo, int velocidade, Sentido sentido = Sentido.Horario, ModosControle modo = ModosControle.AnguloAbsoluto)
public static void Movimento(byte idTx, byte idRx, double angulo, int velocidade, Sentido sentido = Sentido.Horario, ModosControle modo = ModosControle.AnguloAbsoluto)
{
List<byte> payload = new List<byte>();
@ -196,7 +194,7 @@ namespace AgroBase.Services
payload.Add(PulsosBytes[1]);
payload.Add(PulsosBytes[0]);
EnviarComando(Dispositivo, id, (byte)MksFuncCode.ModoControlePulsos, payload.ToArray(), false);
EnviarComando(Dispositivo, idTx, idRx, (byte)MksFuncCode.ModoControlePulsos, payload.ToArray(), false);
}
else
{
@ -211,14 +209,14 @@ namespace AgroBase.Services
payload.AddRange(posInt24); // 3 bytes
byte funcCode = modo == ModosControle.AnguloRelativo ? (byte)MksFuncCode.ModoControleAnguloRelativo : (byte)MksFuncCode.ModoControleAnguloAbsoluto;
EnviarComando(Dispositivo, id, funcCode, payload.ToArray(), false);
EnviarComando(Dispositivo, idTx, idRx, funcCode, payload.ToArray(), false);
}
}
public static void AlterarStatusMotor(byte id, bool Habilitado)
public static void AlterarStatusMotor(byte idTx, byte idRx, bool Habilitado)
{
byte comando = (Habilitado ? (byte)0x01 : (byte)0x00);
EnviarComando(Dispositivo, id, (byte)MksFuncCode.HabilitarMotor, new byte[] { comando }, false);
EnviarComando(Dispositivo, idTx, idRx, (byte)MksFuncCode.HabilitarMotor, new byte[] { comando }, false);
}
#endregion
@ -277,14 +275,14 @@ namespace AgroBase.Services
return valor * 360.0 / 16384.0;
}
private MKS057DModel ObterOuCriar(byte id)
private MKS057DModel ObterOuCriar(byte idTx, byte idRx)
{
lock (DadosLeitura)
{
var item = DadosLeitura.FirstOrDefault(x => x.Endereco == id);
var item = DadosLeitura.FirstOrDefault(x => x.EnderecoTx == idTx && x.EnderecoRx == idRx);
if (item == null)
{
item = new MKS057DModel { Endereco = id };
item = new MKS057DModel { EnderecoTx = idTx, EnderecoRx = idRx };
DadosLeitura.Add(item);
}
return item;
@ -294,10 +292,9 @@ namespace AgroBase.Services
public void ProcessarMensagem(CanMessage mensagem)
{
MksFuncCode func = (MksFuncCode)mensagem.DataRx[0];
byte id = mensagem.IdTx;
var data = mensagem.DataRx;
var item = ObterOuCriar(id);
var item = ObterOuCriar(mensagem.IdTx, mensagem.IdRx);
switch (func)
{

View File

@ -97,7 +97,7 @@ namespace AgroBase.Services
// Verifica e inicializa cada módulo conectado
foreach (var Modulo in Variaveis.OperacaoEmAndamento.DispMvd.Dados.Modulos.Where(x => !x.DirMotor.Inicializado))
{
byte Addr = Modulo.DirMotor.EnderecoByte;
byte Addr = Modulo.DirMotor._EnderecoCAN_Tx;
// Envia comando relevante para verificar o dispositivo
bool envioBemSucedido = await EnviarComandoDriver(MontarComandoRequisicaoVersao(Addr));
@ -114,7 +114,7 @@ namespace AgroBase.Services
DecifrarRespostaDriver(resposta);
if (DadosLeitura.Any(x => x.Endereco == Addr && x.Iniciado))
if (DadosLeitura.Any(x => x.EnderecoTx == Addr && x.Iniciado))
{
Mod_IDs.Add(Modulo.Modulo_ID);
}
@ -158,11 +158,11 @@ namespace AgroBase.Services
foreach (var Mod_ID in Mod_IDs)
{
var Modulo = Variaveis.OperacaoEmAndamento.DispMvd.Dados.Modulos.FirstOrDefault(x => x.Modulo_ID == Mod_ID);
byte Addr = Modulo.DirMotor.EnderecoByte;
byte Addr = Modulo.DirMotor._EnderecoCAN_Tx;
if (!SerialService.DispositivosMapeados.Any(x => x.Dispositivo == T_Code.Dir && x.Mod_ID == Mod_ID))
{
var Leitura = DadosLeitura.FirstOrDefault(x => x.Endereco == Addr);
var Leitura = DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Addr);
if (Leitura != null)
{
SerialService.DispositivosMapeados.Add(new DispositivoDetalhesModel()
@ -180,7 +180,7 @@ namespace AgroBase.Services
private static bool EnderecoValido(byte addr)
{
return Variaveis.OperacaoEmAndamento.DispMvd.Dados.Modulos.Any(x => x.DirMotor.EnderecoByte == addr);
return Variaveis.OperacaoEmAndamento.DispMvd.Dados.Modulos.Any(x => x.DirMotor._EnderecoCAN_Tx == addr);
}
@ -623,8 +623,8 @@ namespace AgroBase.Services
return false;
}
MKS057DModel leitura = DadosLeitura.FirstOrDefault(x => x.Endereco == addr) ?? new MKS057DModel { Endereco = addr };
if (!DadosLeitura.Any(x => x.Endereco == leitura.Endereco))
MKS057DModel leitura = DadosLeitura.FirstOrDefault(x => x.EnderecoTx == addr) ?? new MKS057DModel { EnderecoTx = addr };
if (!DadosLeitura.Any(x => x.EnderecoTx == leitura.EnderecoTx))
{
DadosLeitura.Add(leitura);
}

View File

@ -0,0 +1,395 @@
using AgroBase.Models;
using AgroBase.Models.Modules;
using System;
using System.Collections.Generic;
using System.IO.Ports;
using System.Linq;
using System.Threading.Tasks;
using static AgroBase.Models.Enums;
using static AgroBase.Services.OIDCanService.OidHandler;
namespace AgroBase.Services
{
public class OIDCanService
{
public static List<OIDModel> DadosLeitura = new List<OIDModel>();
private static int _MStep { get; set; } = 16;
private static T_Code Dispositivo { get; set; } = T_Code.Oid;
private static OidHandler _OidHandler { get; set; } = new OidHandler();
private static AsyncTaskTimerModel tmrHeartbeat;
public static bool Iniciado
{
get
{
return CanService.IsConnected && SerialService.DispositivosMapeados.Any(x => x.Dispositivo == T_Code.Mov) && DadosLeitura.Any(x => x.Iniciado);
}
}
public static int TaxaAmostragem
{
get
{
return 300;
}
}
public static async Task<bool> VerificaPortaOID(SerialPort porta)
{
if (!CanService.IsConnected)
{
CanService.DefinirPortaCOM(porta);
}
if (CanService.IsConnected)
{
List<string> Mod_IDs = new List<string>();
// Verifica e inicializa cada módulo conectado
foreach (var Modulo in Variaveis.OperacaoEmAndamento.DispMvd.Dados.Modulos.Where(x => !x.MovMotor.Inicializado))
{
CanService.RegistrarHandler(Modulo.MovMotor._EnderecoCAN_Rx, _OidHandler);
// Envia comando relevante para verificar o dispositivo
RequisitarDado(Modulo.MovMotor._EnderecoCAN_Tx, Modulo.MovMotor._EnderecoCAN_Rx, OidParametros.CodErro);
await Task.Delay(1000);
if (DadosLeitura.Any(x => x.EnderecoRx == Modulo.MovMotor._EnderecoCAN_Rx && x.Iniciado))
{
Mod_IDs.Add(Modulo.Modulo_ID);
}
}
// Define os dispositivos inicializados na lista de dispositivos mapeados
if (Mod_IDs.Any())
{
DefinirDispositivo(Mod_IDs);
}
}
else
{
return false;
}
if (!CanService.Iniciado)
{
CanService.Fechar();
}
return Iniciado;
}
private static void DefinirDispositivo(List<string> Mod_IDs)
{
if (tmrHeartbeat == null || !(tmrHeartbeat?.IsRunning ?? false))
{
tmrHeartbeat?.Dispose();
tmrHeartbeat = new AsyncTaskTimerModel("tmrOidHeartbeat", tmrHeartbeat_Tick, 1000);
tmrHeartbeat.Start();
}
foreach (var Mod_ID in Mod_IDs)
{
var Modulo = Variaveis.OperacaoEmAndamento.DispMvd.Dados.Modulos.FirstOrDefault(x => x.Modulo_ID == Mod_ID).MovMotor;
if (DadosLeitura.Any(x => x.EnderecoTx == Modulo._EnderecoCAN_Tx && !x.Configurado))
{
ConfigurarDriver(Modulo);
}
if (!SerialService.DispositivosMapeados.Any(x => x.Dispositivo == T_Code.Mov && x.Mod_ID == Mod_ID))
{
var Leitura = DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Modulo._EnderecoCAN_Tx);
if (Leitura != null)
{
SerialService.DispositivosMapeados.Add(new DispositivoDetalhesModel()
{
Endereco = CanService._portName,
Dispositivo = T_Code.Mov,
Erro = Leitura.CodigoAlarme > 0,
Versao = "1.0",
Mod_ID = Mod_ID,
});
}
}
}
}
#region COMANDOS
private static void EnviarComando(T_Code Dispositivo, byte idTx, byte idRx, byte funcCode, byte[] payload = null, bool get = true)
{
CanService.AdicionarMensagemNaFila(Dispositivo, idTx, idRx, funcCode, funcCode, payload, get);
}
public static void RequisitarDado(byte idTx, byte idRx, OidParametros dado)
{
EnviarComando(Dispositivo, idTx, idRx, (byte)OidFuncCode.Consulta, new byte[] { (byte)dado });
}
public static void ComandoControle(byte idTx, byte idRx, OidFuncCode tipoControle, double setPoint)
{
byte[] setPointBytes = null;
switch (tipoControle)
{
case OidFuncCode.ComandoCorrente:
case OidFuncCode.ComandoCorrenteFreio:
case OidFuncCode.AjusteCorrenteMaxima:
{
short corrente_10mA = (short)(setPoint * 100);
setPointBytes = BitConverter.GetBytes(corrente_10mA);
break;
}
case OidFuncCode.ComandoVelocidade:
{
int erpm = (int)(setPoint * VariaveisEquipamento.NumeroPolosMotor);
setPointBytes = BitConverter.GetBytes(erpm);
break;
}
case OidFuncCode.ComandoCicloTrabalho:
{
short duty = (short)(Math.Max(-100, Math.Min(setPoint, 100)) * 10);
setPointBytes = BitConverter.GetBytes(duty);
break;
}
case OidFuncCode.AjusteAceleracaoVelocidade:
case OidFuncCode.AjusteDesaceleracaoVelocidade:
{
double erpmMax = VariaveisEquipamento.RPM_Max_Roda * VariaveisEquipamento.RelacaoRPM * VariaveisEquipamento.NumeroPolosMotor;
int aceleracao = (int)(erpmMax / setPoint); // setPoint = tempo (s)
setPointBytes = BitConverter.GetBytes(aceleracao);
break;
}
case OidFuncCode.Heartbeat:
{
setPointBytes = new byte[] { (byte)setPoint };
break;
}
default:
{
Console.WriteLine($"[OID] Comando nao mapeado: {tipoControle.ToString()}");
break;
}
}
if (setPointBytes == null)
return;
if (BitConverter.IsLittleEndian)
Array.Reverse(setPointBytes);
EnviarComando(Dispositivo, idTx, idRx, (byte)tipoControle, setPointBytes);
}
private static void ConfigurarDriver(MovimentacaoModel Modulo)
{
byte addrTx = Modulo._EnderecoCAN_Tx;
byte addrRx = Modulo._EnderecoCAN_Rx;
ComandoControle(addrTx, addrRx, OidFuncCode.ComandoCorrenteFreio, 3.0);
ComandoControle(addrTx, addrRx, OidFuncCode.ComandoVelocidade, 0.0);
ComandoControle(addrTx, addrRx, OidFuncCode.AjusteCorrenteMaxima, Modulo.CorrenteTorqueMaximo);
ComandoControle(addrTx, addrRx, OidFuncCode.AjusteAceleracaoVelocidade, Modulo.Rampa);
ComandoControle(addrTx, addrRx, OidFuncCode.AjusteDesaceleracaoVelocidade, Modulo.Rampa);
DadosLeitura.Where(x => x.EnderecoTx == addrTx).First().Configurado = true;
}
#endregion
private static async Task tmrHeartbeat_Tick()
{
foreach (var Mod in Variaveis.OperacaoEmAndamento.DispMvd?.Dados?.Modulos)
{
if (Mod.MovMotor.Inicializado)
{
int novoValor = Mod.MovMotor.heartBeatValue == 0 ? 1 : 0;
ComandoControle(Mod.MovMotor._EnderecoCAN_Tx, Mod.MovMotor._EnderecoCAN_Rx, OidFuncCode.Heartbeat, novoValor);
}
}
}
public class OidHandler : ICanMessageHandler
{
public enum OidFuncCode : byte
{
Heartbeat = 0x00,
ComandoCorrente = 0x01,
ComandoVelocidade = 0x02,
ComandoCicloTrabalho = 0x03,
ComandoPosicaoAbsoluta = 0x04,
ComandoIncrementoPosicaoRelativaAnterior = 0x05,
ComandoIncrementoPosicaoRelativaAtual = 0x06,
ComandoPosicaoAtual = 0x07,
ComandoCorrenteFreio= 0x08,
ComandoCorrenteFreioMao = 0x09,
AjusteAceleracaoVelocidade = 0x0A,
AjusteVelocidadeMaxima = 0x0B,
AjusteAceleracaoeMaxima = 0x0C,
AjusteDesaceleracaoeMaxima = 0x0D,
AlterarTabelaConfiguracao = 0x0E,
Consulta = 0x0F,
AjusteDesaceleracaoVelocidade = 0x10,
ComandoRetornarZero = 0x11,
ComandoCancelarRetornoZero = 0x12,
ConsultaStatusRetornoZero = 0x13,
AjusteCorrenteMaxima = 0x14,
AjusteAceleracaoSubidaTorque = 0x15,
AjusteRampaTorque = 0x16,
}
public enum OidParametros : byte
{
CodErro = 0,
VelocidadeAtual = 1,
CicloTrabalho = 2,
Potencia = 3,
Tensao = 4,
CorrenteMotor = 5,
CorrenteBarramento = 6,
Temperatura = 7,
PosicaoAbsoluta = 8,
PosicaoRelativa = 9,
ModoCodificador = 10,
ErroLerCache = 11,
IO_Status = 12
}
public enum OidCodigoErro : byte
{
NenhumErro = 0,
Sobretensao = 1,
Subtensao = 2,
CorrenteMaximaExcedida = 3,
TemperaturaMOS = 4,
SubtensaoMCU = 5,
Watchdog = 6,
ErroSPI = 7,
FlashDanificado = 8,
DeslocamentoSensorU = 9,
DeslocamentoSensorV = 10,
DeslocamentoSensorW = 11,
DesequilibrioTrifasico = 12,
MotorFlashCorrompido = 13,
AplicacaoFlashCorrompida = 14,
PulsacaoCANOPEN = 15,
Parado = 16,
Parar = 17,
ForaDeTolerancia = 18,
SinalZNaoEncontrado = 19
}
private OIDModel ObterOuCriar(byte idTx, byte idRx)
{
lock (DadosLeitura)
{
var item = DadosLeitura.FirstOrDefault(x => x.EnderecoTx == idTx && x.EnderecoRx == idRx);
if (item == null)
{
item = new OIDModel { EnderecoTx = idTx, EnderecoRx = idRx };
DadosLeitura.Add(item);
}
return item;
}
}
public void ProcessarMensagem(CanMessage mensagem)
{
OidFuncCode func = (OidFuncCode)mensagem.DataRx[0];
OidParametros parametro = (OidParametros)mensagem.DataRx[1];
byte[] valorBytes = mensagem.DataRx.Skip(2).ToArray();
if (BitConverter.IsLittleEndian)
Array.Reverse(valorBytes);
var item = ObterOuCriar(mensagem.IdTx, mensagem.IdRx);
try
{
switch (parametro)
{
case OidParametros.CodErro:
if (valorBytes.Length >= 2)
{
short codigo = BitConverter.ToInt16(valorBytes, 0);
item.CodigoAlarme = (OidCodigoErro)codigo;
}
break;
case OidParametros.VelocidadeAtual:
if (valorBytes.Length == 4)
item.ERPM = BitConverter.ToInt32(valorBytes, 0);
break;
case OidParametros.CicloTrabalho:
if (valorBytes.Length >= 2)
item.CicloTrabalho = BitConverter.ToInt16(valorBytes, 0) / 10.0; // em %
break;
case OidParametros.Potencia:
if (valorBytes.Length >= 2)
item.Potencia = BitConverter.ToInt16(valorBytes, 0); // em Watts
break;
case OidParametros.Tensao:
if (valorBytes.Length >= 2)
item.Tensao = BitConverter.ToInt16(valorBytes, 0); // em Volts
break;
case OidParametros.CorrenteMotor:
if (valorBytes.Length >= 2)
item.CorrenteMotor = BitConverter.ToInt16(valorBytes, 0) / 100.0; // em A
break;
case OidParametros.CorrenteBarramento:
if (valorBytes.Length >= 2)
item.CorrenteBarramento = BitConverter.ToInt16(valorBytes, 0) / 100.0; // em A
break;
case OidParametros.Temperatura:
if (valorBytes.Length >= 2)
item.Temperatura = BitConverter.ToInt16(valorBytes, 0); // em °C
break;
case OidParametros.PosicaoAbsoluta:
if (valorBytes.Length == 4)
item.PosicaoAbsoluta = BitConverter.ToInt32(valorBytes, 0) / 100.0; // em graus
break;
case OidParametros.PosicaoRelativa:
if (valorBytes.Length == 4)
item.PosicaoRelativa = BitConverter.ToInt32(valorBytes, 0) / 100.0; // em graus
break;
case OidParametros.ModoCodificador:
if (valorBytes.Length >= 2)
item.ModoCodificador = BitConverter.ToInt16(valorBytes, 0); // 0 ou 1 geralmente
break;
case OidParametros.ErroLerCache:
if (valorBytes.Length >= 2)
item.ErroHistorico = BitConverter.ToInt16(valorBytes, 0);
break;
case OidParametros.IO_Status:
if (valorBytes.Length >= 2)
item.IO_Status = BitConverter.ToUInt16(valorBytes, 0); // leitura binária
break;
}
item.UltimoComandoRecebido = DateTime.Now;
}
catch (Exception ex)
{
Console.WriteLine($"[OID] Erro ao interpretar resposta CAN ({parametro}): {ex.Message}");
}
}
}
}
}

View File

@ -8,7 +8,7 @@ using static AgroBase.Models.Enums;
namespace AgroBase.Services
{
public class OIDService
public class OIDRs485Service
{
public static List<ModbusParametrosModel> Parametros = new List<ModbusParametrosModel>()
{
@ -481,7 +481,7 @@ namespace AgroBase.Services
}
public static int TaxaAmostragem { get; set; } = 1000;
public static List<OIDModel> DadosLeitura = new List<OIDModel>();
public static List<OID485Model> DadosLeitura = new List<OID485Model>();
private static List<OIDComandoModel> FilaComandos = new List<OIDComandoModel>();
@ -562,14 +562,14 @@ namespace AgroBase.Services
byte Addr = 0;
try
{
Addr = Modulo.MovMotor.EnderecoByte;
Addr = Modulo.MovMotor._EnderecoCAN_Tx;
}
catch
{
RegisrarErrosComunicacao(Addr, $"Erro ao definir endereço");
}
if (DadosLeitura.Any(x => x.Endereco == Addr && x.Iniciado))
if (DadosLeitura.Any(x => x.EnderecoTx == Addr && x.Iniciado))
{
continue;
}
@ -598,7 +598,7 @@ namespace AgroBase.Services
DecifrarResposta(resposta, Comando);
if (DadosLeitura.Any(x => x.Endereco == Addr && x.Iniciado))
if (DadosLeitura.Any(x => x.EnderecoTx == Addr && x.Iniciado))
{
Mod_IDs.Add(Modulo.Modulo_ID);
}
@ -752,16 +752,16 @@ namespace AgroBase.Services
foreach (var Mod_ID in Mod_IDs)
{
var Modulo = Variaveis.OperacaoEmAndamento.DispMvd.Dados.Modulos.FirstOrDefault(x => x.Modulo_ID == Mod_ID);
byte Addr = Modulo.MovMotor.EnderecoByte;
byte Addr = Modulo.MovMotor._EnderecoCAN_Tx;
if (DadosLeitura.Any(x => x.Endereco == Addr && !x.Configurado))
if (DadosLeitura.Any(x => x.EnderecoTx == Addr && !x.Configurado))
{
ConfigurarDriver(Addr);
}
if (!SerialService.DispositivosMapeados.Any(x => x.Dispositivo == T_Code.Mov && x.Mod_ID == Mod_ID))
{
var leitura = DadosLeitura.FirstOrDefault(x => x.Endereco == Addr);
var leitura = DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Addr);
SerialService.DispositivosMapeados.Add(new DispositivoDetalhesModel()
{
Endereco = _ethernetService != null ? _ethernetService._ipAddress : "N/A",
@ -776,7 +776,7 @@ namespace AgroBase.Services
private static void ConfigurarDriver(byte Addr)
{
var Modulo = Variaveis.OperacaoEmAndamento.DispMvd.Dados.Modulos.FirstOrDefault(x => x.MovMotor.EnderecoByte == Addr);
var Modulo = Variaveis.OperacaoEmAndamento.DispMvd.Dados.Modulos.FirstOrDefault(x => x.MovMotor._EnderecoCAN_Tx == Addr);
AdicionarComandoNaFila(new OIDComandoModel()
{
Endereco = Addr,
@ -840,7 +840,7 @@ namespace AgroBase.Services
Parametro = Parametros.First(x => x.Chave == "RampaDescidaVelocidade"),
Valor = Modulo.MovMotor.Rampa
});
DadosLeitura.Where(x => x.Endereco == Addr).First().Configurado = true;
DadosLeitura.Where(x => x.EnderecoTx == Addr).First().Configurado = true;
}
@ -853,12 +853,12 @@ namespace AgroBase.Services
RegisrarComandosComunicacao(Addr, $"RX: - {BitConverter.ToString(resposta ?? new byte[] { }).Replace("-", " ")}");
var Leitura = DadosLeitura.FirstOrDefault(x => x.Endereco == Addr);
var Leitura = DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Addr);
if (Leitura == null)
{
Leitura = new OIDModel()
Leitura = new OID485Model()
{
Endereco = Addr,
EnderecoTx = Addr,
UltimoComandoRecebido = DateTime.MinValue,
parametros = new List<OIDParametrosRequisitar>()
{
@ -1052,12 +1052,12 @@ namespace AgroBase.Services
if (Mod.MovMotor.Inicializado)
{
var Parametro = Parametros.First(x => x.Chave == "Heartbeat");
int valor = DadosLeitura.FirstOrDefault(x => x.Endereco == Mod.MovMotor.EnderecoByte && x.parametros.Any(y => y.Registro == Parametro.Registro))?.Heartbeat ?? 0;
int valor = DadosLeitura.FirstOrDefault(x => x.EnderecoTx == Mod.MovMotor._EnderecoCAN_Tx && x.parametros.Any(y => y.Registro == Parametro.Registro))?.Heartbeat ?? 0;
int novoValor = valor == 0 ? 1 : 0;
AdicionarComandoNaFila(new OIDComandoModel()
{
Endereco = Mod.MovMotor.EnderecoByte,
Endereco = Mod.MovMotor._EnderecoCAN_Tx,
AguardaResposta = false,
TimeoutResposta = 10,
Get = false,

View File

@ -29,7 +29,7 @@ namespace AgroBase.Services
public static List<T_Code> DispositivosConexaoInicial = new List<T_Code>() { T_Code.Mvd, T_Code.Atu, T_Code.Sen };
public static List<T_Code> DispositivosProprios = new List<T_Code>() { T_Code.Atu, T_Code.Sen };
public static List<T_Code> DispositivosModbus = new List<T_Code>() { T_Code.Pzm, T_Code.Wit, T_Code.A05 };
public static List<T_Code> DispositivosCan = new List<T_Code>() { T_Code.Dir, T_Code.Mks, T_Code.Sen, T_Code.Atu };
public static List<T_Code> DispositivosCan = new List<T_Code>() { T_Code.Mov, T_Code.Oid, T_Code.Dir, T_Code.Mks, T_Code.Sen, T_Code.Atu };
public static List<T_Code> DispositivosMultiplos = new List<T_Code>() { T_Code.Bld, T_Code.Mks, T_Code.Mvd, T_Code.Oid, T_Code.Mov, T_Code.Dir };
public static List<DispositivoDetalhesModel> DispositivosMapeados = new List<DispositivoDetalhesModel>();
@ -274,10 +274,10 @@ namespace AgroBase.Services
ProcurarDispositivosUSB();
if (Variaveis.OperacaoEmAndamento.DispMvd != null)
/*if (Variaveis.OperacaoEmAndamento.DispMvd != null)
{
await ProcurarDispositivosEthernet();
}
}*/
/*if (ModbusService.Iniciado)
{
@ -565,6 +565,12 @@ namespace AgroBase.Services
}
bool DispOid = await ProcuraDispositivoOID(porta);
if (DispOid)
{
}
return CanService.Iniciado;
}
@ -596,11 +602,11 @@ namespace AgroBase.Services
ethernetEncontrado = true;
}*/
bool DispOid = await ProcuraDispositivoOID();
/*bool DispOid = await ProcuraDispositivoOID();
if (DispOid)
{
ethernetEncontrado = true;
}
}*/
/*bool DispMks = await ProcuraDispositivoMKS();
if (DispMks)
@ -630,12 +636,12 @@ namespace AgroBase.Services
return BLD300RService.Iniciado;
}
private static async Task<bool> ProcuraDispositivoOID()
private static async Task<bool> ProcuraDispositivoOID(SerialPort porta)
{
if (!OIDService.Iniciado || OIDService.DadosLeitura.Count(x => x.Iniciado) < (Variaveis.OperacaoEmAndamento.DispMvd?.Dados?.Modulos?.Count() ?? 4))
if (!OIDCanService.Iniciado || OIDCanService.DadosLeitura.Count(x => x.Iniciado) < (Variaveis.OperacaoEmAndamento.DispMvd?.Dados?.Modulos?.Count() ?? 4))
{
AtualizarConsole("Procurando dispositivos OID");
bool Encontrado = await OIDService.VerificaPortaOID();
bool Encontrado = await OIDCanService.VerificaPortaOID(porta);
if (Encontrado)
{
AtualizarConsole("Dispositivo OID encontrado");
@ -643,7 +649,7 @@ namespace AgroBase.Services
}
}
return OIDService.Iniciado;
return OIDCanService.Iniciado;
}
private static async Task<bool> ProcuraDispositivoMKS(SerialPort porta)

View File

@ -1 +1 @@
{"tmrRegistrador":{"_uiControl":null,"State":2,"IsRunning":false,"IsStopped":true,"IsCreated":false,"Interval":1000,"StackTrace":"AtuadorModel.IniciarRegistrador","Id":"tmrRegistrador_Atu","TimeTick":"00:00:00"},"_AtuHandler":{},"Dispositivo":103,"Modulo_ID":"Atu","_EnderecoCAN":18,"_TaxaAmostragem":1000,"RequisitarDados":true,"Conectado":false,"QuantidadeBicos":4,"DensidadeHerbicida":1.1,"BicosPulverizadores":[{"ID":"B01","ID_Num":71,"Posicao":1,"Componente":11,"AtuacaoNivelAlto":true,"ComandoAtuar":false,"Comandar":true,"Testando":false,"Funcoes":[21],"LeituraStatusBico":false,"MediaNivelFluxo":0.0,"Leitura":null,"Inicializado":false,"Atuacoes":0,"InicioAtuacao":"0001-01-01T00:00:00","TempoAtuado":0.0},{"ID":"B02","ID_Num":72,"Posicao":2,"Componente":11,"AtuacaoNivelAlto":true,"ComandoAtuar":false,"Comandar":true,"Testando":false,"Funcoes":[21],"LeituraStatusBico":false,"MediaNivelFluxo":0.0,"Leitura":null,"Inicializado":false,"Atuacoes":0,"InicioAtuacao":"0001-01-01T00:00:00","TempoAtuado":0.0},{"ID":"B03","ID_Num":73,"Posicao":3,"Componente":11,"AtuacaoNivelAlto":true,"ComandoAtuar":false,"Comandar":true,"Testando":false,"Funcoes":[21],"LeituraStatusBico":false,"MediaNivelFluxo":0.0,"Leitura":null,"Inicializado":false,"Atuacoes":0,"InicioAtuacao":"0001-01-01T00:00:00","TempoAtuado":0.0},{"ID":"B04","ID_Num":74,"Posicao":4,"Componente":11,"AtuacaoNivelAlto":true,"ComandoAtuar":false,"Comandar":true,"Testando":false,"Funcoes":[21],"LeituraStatusBico":false,"MediaNivelFluxo":0.0,"Leitura":null,"Inicializado":false,"Atuacoes":0,"InicioAtuacao":"0001-01-01T00:00:00","TempoAtuado":0.0}],"BombasPressurizadoras":[{"ID":"BOMBA","ID_Num":51,"ComandoAtuar":false,"Componente":14,"LeituraEstado":false,"Comandar":true,"Testando":false,"Funcoes":[14,35,36,37,5],"LeituraPotencia":0.0,"LeituraPressaoSP":0.0,"LeituraPressao":0.0,"Leitura":null,"Inicializado":false}],"Sensores":[{"LogGrafico":[],"ID":"FLXLN","ID_Num":61,"Descricao":"Fluxo na linha principal","Componente":8,"Aferir":true,"Leitura":null,"Inicializado":false,"Funcoes":[25],"Parametros":[],"UnidadeMedida":"mL/s","LimiteMaximo":0.0,"LimiteMinimo":0.0},{"LogGrafico":[],"ID":"MASRS","ID_Num":62,"Descricao":"Massa do reservatório de herbicida","Componente":10,"Aferir":true,"Leitura":null,"Inicializado":false,"Funcoes":[22,23],"Parametros":[],"UnidadeMedida":"Kg","LimiteMaximo":0.0,"LimiteMinimo":0.0},{"LogGrafico":[],"ID":"PRSLN","ID_Num":63,"Descricao":"Pressão na linha principal","Componente":12,"Aferir":true,"Leitura":null,"Inicializado":false,"Funcoes":[24],"Parametros":[{"Descricao":"Vmin","Valor":"0","QtdBytes":1,"Escalar":false,"Enviar":false},{"Descricao":"Vmax","Valor":"4.5","QtdBytes":1,"Escalar":true,"Enviar":false},{"Descricao":"Pmax","Valor":"174","QtdBytes":1,"Escalar":false,"Enviar":false}],"UnidadeMedida":"psi","LimiteMaximo":0.0,"LimiteMinimo":0.0}],"BombaPressurizadora":{"ID":"BOMBA","ID_Num":51,"ComandoAtuar":false,"Componente":14,"LeituraEstado":false,"Comandar":true,"Testando":false,"Funcoes":[14,35,36,37,5],"LeituraPotencia":0.0,"LeituraPressaoSP":0.0,"LeituraPressao":0.0,"Leitura":null,"Inicializado":false},"ScriptDeteccaoErvas":"weed_detector_oak-1_0.py","DadosLeitura":{"Momento":"0001-01-01T00:00:00","Conectado":false,"Dispositivo":0,"Versao":0,"Mod_ID":null,"QualidadeWifi":0,"LatenciaLoop":0,"BicosPulverizadores":[],"BombasPressurizadoras":[],"SensoresFluxo":[],"SensoresMassa":[],"SensoresPressao":[],"UltimoComandoRespondido":"0001-01-01T00:00:00"},"_MassaRef":0.8,"_MassaLeituraRef":40876.37,"_MassaLeituraExtra":1895800.0,"MassaReservatorio":0.0,"VolumeReservatorio":0.0,"PercentualReservatorio":0.0,"VolumeVazaoAferido":0.0,"_FluxoMlRef":600.0,"_FluxoPulsoRef":538.0,"VazaoFluxoMLpSInstantanea":0.0,"VazaoFluxoMLpSMedia":0.0,"VolumeVazaoML":0.0,"InicioAtuacao":"0001-01-01T00:00:00","TempoAtuado":0.0,"_PressaoVmin":0.0,"_PressaoVmax":4.5,"_PressaoMax":174.045,"PressaoLinha":0.0,"PressaoLinhaCalc":0.0,"PercentualErvasTerreno":0.0}
{"tmrRegistrador":{"_uiControl":null,"State":2,"IsRunning":false,"IsStopped":true,"IsCreated":false,"Interval":1000,"StackTrace":"AtuadorModel.IniciarRegistrador","Id":"tmrRegistrador_Atu","TimeTick":"00:00:00"},"_AtuHandler":{},"Dispositivo":103,"Modulo_ID":"Atu","_EnderecoCAN_Tx":19,"_EnderecoCAN_Rx":20,"_TaxaAmostragem":1000,"RequisitarDados":true,"Conectado":false,"QuantidadeBicos":4,"DensidadeHerbicida":1.1,"BicosPulverizadores":[{"ID":"B01","ID_Num":71,"Posicao":1,"Componente":11,"AtuacaoNivelAlto":true,"ComandoAtuar":false,"Comandar":true,"Testando":false,"Funcoes":[21],"LeituraStatusBico":false,"MediaNivelFluxo":0.0,"Leitura":null,"Inicializado":false,"Atuacoes":0,"InicioAtuacao":"0001-01-01T00:00:00","TempoAtuado":0.0},{"ID":"B02","ID_Num":72,"Posicao":2,"Componente":11,"AtuacaoNivelAlto":true,"ComandoAtuar":false,"Comandar":true,"Testando":false,"Funcoes":[21],"LeituraStatusBico":false,"MediaNivelFluxo":0.0,"Leitura":null,"Inicializado":false,"Atuacoes":0,"InicioAtuacao":"0001-01-01T00:00:00","TempoAtuado":0.0},{"ID":"B03","ID_Num":73,"Posicao":3,"Componente":11,"AtuacaoNivelAlto":true,"ComandoAtuar":false,"Comandar":true,"Testando":false,"Funcoes":[21],"LeituraStatusBico":false,"MediaNivelFluxo":0.0,"Leitura":null,"Inicializado":false,"Atuacoes":0,"InicioAtuacao":"0001-01-01T00:00:00","TempoAtuado":0.0},{"ID":"B04","ID_Num":74,"Posicao":4,"Componente":11,"AtuacaoNivelAlto":true,"ComandoAtuar":false,"Comandar":true,"Testando":false,"Funcoes":[21],"LeituraStatusBico":false,"MediaNivelFluxo":0.0,"Leitura":null,"Inicializado":false,"Atuacoes":0,"InicioAtuacao":"0001-01-01T00:00:00","TempoAtuado":0.0}],"BombasPressurizadoras":[{"ID":"BOMBA","ID_Num":51,"ComandoAtuar":false,"Componente":14,"LeituraEstado":false,"Comandar":true,"Testando":false,"Funcoes":[14,35,36,37,5],"LeituraPotencia":0.0,"LeituraPressaoSP":0.0,"LeituraPressao":0.0,"Leitura":null,"Inicializado":false}],"Sensores":[{"LogGrafico":[],"ID":"FLXLN","ID_Num":61,"Descricao":"Fluxo na linha principal","Componente":8,"Aferir":true,"Leitura":null,"Inicializado":false,"Funcoes":[25],"Parametros":[],"UnidadeMedida":"mL/s","LimiteMaximo":0.0,"LimiteMinimo":0.0},{"LogGrafico":[],"ID":"MASRS","ID_Num":62,"Descricao":"Massa do reservatório de herbicida","Componente":10,"Aferir":true,"Leitura":null,"Inicializado":false,"Funcoes":[22,23],"Parametros":[],"UnidadeMedida":"Kg","LimiteMaximo":0.0,"LimiteMinimo":0.0},{"LogGrafico":[],"ID":"PRSLN","ID_Num":63,"Descricao":"Pressão na linha principal","Componente":12,"Aferir":true,"Leitura":null,"Inicializado":false,"Funcoes":[24],"Parametros":[{"Descricao":"Vmin","Valor":"0","QtdBytes":1,"Escalar":false,"Enviar":false},{"Descricao":"Vmax","Valor":"4.5","QtdBytes":1,"Escalar":true,"Enviar":false},{"Descricao":"Pmax","Valor":"174","QtdBytes":1,"Escalar":false,"Enviar":false}],"UnidadeMedida":"psi","LimiteMaximo":0.0,"LimiteMinimo":0.0}],"BombaPressurizadora":{"ID":"BOMBA","ID_Num":51,"ComandoAtuar":false,"Componente":14,"LeituraEstado":false,"Comandar":true,"Testando":false,"Funcoes":[14,35,36,37,5],"LeituraPotencia":0.0,"LeituraPressaoSP":0.0,"LeituraPressao":0.0,"Leitura":null,"Inicializado":false},"ScriptDeteccaoErvas":"weed_detector_oak-1_0.py","DadosLeitura":{"Momento":"0001-01-01T00:00:00","Conectado":false,"Dispositivo":0,"Versao":0,"Mod_ID":null,"QualidadeWifi":0,"LatenciaLoop":0,"BicosPulverizadores":[],"BombasPressurizadoras":[],"SensoresFluxo":[],"SensoresMassa":[],"SensoresPressao":[],"UltimoComandoRespondido":"0001-01-01T00:00:00"},"_MassaRef":0.8,"_MassaLeituraRef":40876.37,"_MassaLeituraExtra":1895800.0,"MassaReservatorio":0.0,"VolumeReservatorio":0.0,"PercentualReservatorio":0.0,"VolumeVazaoAferido":0.0,"_FluxoMlRef":600.0,"_FluxoPulsoRef":538.0,"VazaoFluxoMLpSInstantanea":0.0,"VazaoFluxoMLpSMedia":0.0,"VolumeVazaoML":0.0,"InicioAtuacao":"0001-01-01T00:00:00","TempoAtuado":0.0,"_PressaoVmin":0.0,"_PressaoVmax":4.5,"_PressaoMax":174.045,"PressaoLinha":0.0,"PressaoLinhaCalc":0.0,"PercentualErvasTerreno":0.0}

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@ -1 +1 @@
94e5acd4ef698303080886ab8e455321319e02e14c31bfb9f4f93b4ef716322c
f56f6e797f3d17381a454591f16b6e30ab659a2f5d6fa08cd131c877ba5db632

View File

@ -157,8 +157,8 @@ class BombaPressurizadora {
std::vector<uint8_t> MontarMensagemCAN(CanMessagePosicaoDados posicao) {
std::vector<uint8_t> data;
data.push_back(ID_Num);
data.push_back(static_cast<uint8_t>(posicao));
data.push_back(ID_Num);
switch (posicao) {
case CanMessagePosicaoDados::Status: {
data.push_back(Iniciado ? 1 : 0);
@ -191,19 +191,19 @@ class BombaPressurizadora {
std::vector<uint8_t> BombaPressurizadora::ConfigurarBomba(std::vector<BombaPressurizadora*>& lista, std::vector<uint8_t>& data, const String& Mod_ID, std::vector<SensorPressao*>& sensoresPressao) {
std::vector<uint8_t> status;
if (data.size() < 3) return status;
if (data.size() < 2) return status;
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[0];
uint8_t idNum = data[1];
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[2];
auto it = std::find_if(lista.begin(), lista.end(), [idNum](BombaPressurizadora* s) { return s->ID_Num == idNum; });
bool jaExiste = it != lista.end();
BombaPressurizadora* bomba;
switch (posicao) {
case CanMessagePosicaoDados::Config1: {
if (data.size() < 8) return status;
bool conectar = data[4] == 1;
int pressaoSp = (int)data[5];
int pinoEn = data[6];
int pinoCs = data[7];
if (data.size() < 7) return status;
bool conectar = data[3] == 1;
int pressaoSp = (int)data[4];
int pinoEn = data[5];
int pinoCs = data[6];
if (conectar) {
if (!jaExiste) {
bomba = new BombaPressurizadora(Mod_ID, "sBMB_" + String(idNum));
@ -245,12 +245,12 @@ std::vector<uint8_t> BombaPressurizadora::ConfigurarBomba(std::vector<BombaPress
break;
}
case CanMessagePosicaoDados::Config2: {
if (data.size() < 7) return status;
if (data.size() < 6) return status;
if (!jaExiste) return status;
int pinoIna = data[4];
int pinoInb = data[5];
int pinoPwm = data[6];
int pinoIna = data[3];
int pinoInb = data[4];
int pinoPwm = data[5];
bomba = *it;
if (!bomba->Iniciado) {

View File

@ -94,7 +94,7 @@ class CanService {
uint8_t ID_Num_sMOD = 0;
uint8_t ID_Num_sTOD = 250;
uint8_t ID_Num_sLRA = 251;
typedef void (*OnReceiveCallback)(int packetSize, int senderId, byte funcCode, byte* data, int dataLength);
typedef void (*OnReceiveCallback)(int packetSize, int senderId, CanMessagePosicaoDados posicao, byte* data, int dataLength);
CanService(uint8_t nodeId, uint32_t baudRate = 500000) {
_nodeId = nodeId;
@ -239,9 +239,9 @@ class CanService {
while (true) {
if (xQueueReceive(service->canQueueRx, &msg, portMAX_DELAY) == pdTRUE) {
//PrintTela("[CAN] Mensagem recebida da fila RX");
uint8_t funcCode = msg.data[0];
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)msg.data[0];
if (service->_callback) {
service->_callback(msg.data_length_code, msg.identifier, funcCode, &msg.data[1], msg.data_length_code - 1);
service->_callback(msg.data_length_code, msg.identifier, posicao, &msg.data[1], msg.data_length_code - 1);
}
}
vTaskDelay(1);
@ -255,7 +255,7 @@ class CanService {
for (UBaseType_t i = 0; i < items; i++) {
if (xQueuePeek(fila, &msgTmp, 0) == pdTRUE) {
if (msgTmp.identifier == novaMsg.identifier && msgTmp.data[0] == novaMsg.data[0] && msgTmp.data[1] == novaMsg.data[1] && msgTmp.data[2] == novaMsg.data[2]) {
if (msgTmp.identifier == novaMsg.identifier && msgTmp.data[0] == novaMsg.data[0] && msgTmp.data[1] == novaMsg.data[1]) {
return true; // já tem uma igual
}
}
@ -302,16 +302,44 @@ class CanService {
}
std::vector<uint8_t> MontarFrameChk(T_Code D_Code, bool Conectado, int Versao) {
F_Code FuncaoPorPosicao(CanMessagePosicaoDados posicao) {
F_Code funcao = F_Code::Nda;
int pos = static_cast<int>(posicao);
if (pos >= 0 && pos <= 50) {
funcao = F_Code::ReqTx;
}
else if (pos > 50 && pos <= 100) {
funcao = F_Code::CfgTx;
}
else if (pos > 100 && pos <= 150) {
funcao = F_Code::CmdTx;
}
//PrintTela("Funcao parseada para posicao: " + String(pos) + ", funcao: " + String(funcao));
return funcao;
}
std::vector<uint8_t> MontarFrameReqStatusMod(T_Code D_Code, bool Conectado, int Versao) {
std::vector<uint8_t> data;
data.push_back(ID_Num_sMOD);
data.push_back(static_cast<uint8_t>(CanMessagePosicaoDados::Status));
data.push_back(ID_Num_sMOD);
data.push_back(static_cast<uint8_t>(D_Code));
data.push_back(Conectado ? 1 : 0);
data.push_back(Versao);
return data;
}
std::vector<uint8_t> MontarFrameReqDadosFim(int latencia) {
std::vector<uint8_t> data;
data.push_back(static_cast<uint8_t>(CanMessagePosicaoDados::DadosAll));
data.push_back(ID_Num_sTOD);
data.push_back(latencia);
return data;
}
private:
uint8_t _nodeId;
uint32_t _baudRate;

View File

@ -24,9 +24,17 @@ class I2CService {
static SemaphoreHandle_t i2cMutex;
static void DefinirPinos(int sda, int scl) {
static bool DefinirPinos(int sda, int scl) {
bool mudou = false;
if (_pinoSDA != sda) {
_pinoSDA = sda;
mudou = true;
}
if (_pinoSCL != scl) {
_pinoSCL = scl;
mudou = true;
}
return mudou;
}
static bool IniciarI2C() {

View File

@ -102,8 +102,8 @@ public:
std::vector<uint8_t> MontarMensagemCAN(CanMessagePosicaoDados posicao) {
std::vector<uint8_t> data;
data.push_back(_canService->ID_Num_sLRA);
data.push_back(static_cast<uint8_t>(posicao));
data.push_back(_canService->ID_Num_sLRA);
switch (posicao) {
case CanMessagePosicaoDados::Status: {
data.push_back(Conectado ? 1 : 0);
@ -123,9 +123,9 @@ public:
}
void EnviarComando(std::vector<uint8_t> dados) {
if (dados.size() < 3) return;
if (dados.size() < 2) return;
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)dados[0];
uint8_t idNum = dados[1];
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)dados[2];
switch (posicao) {
case CanMessagePosicaoDados::Command1: {
bool sucesso = requisitarParametrosLoRa();
@ -151,46 +151,47 @@ public:
std::vector<uint8_t> ConfigurarModulo(std::vector<uint8_t> data) {
std::vector<uint8_t> status;
if (data.size() < 3) return status;
if (data.size() < 2) return status;
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[0];
uint8_t idNum = data[1];
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[2];
PrintTela("[LRA] Recebido comando ConfigurarModulo: posicao = " + String((int)posicao));
switch (posicao) {
case CanMessagePosicaoDados::Config1: {
if (data.size() < 8) return data;
_pinM0 = data[3];
_pinM1 = data[4];
_pinAUX = data[5];
_pinRXD = data[6];
_pinTXD = data[7];
if (data.size() < 7) return data;
_pinM0 = data[2];
_pinM1 = data[3];
_pinAUX = data[4];
_pinRXD = data[5];
_pinTXD = data[6];
break;
}
case CanMessagePosicaoDados::Config2: {
if (data.size() < 8) return data;
if (data.size() < 7) return data;
if (_pinRXD == 0 || _pinTXD == 0) {
PrintTela("[LRA] Erro ao iniciar E220, pinout ainda nao definido!");
return status;
}
uint8_t baudField = data[4] & 0xE0; // bits 5,6,7 (baudrate)
uint8_t addr = data[2]; // address
uint8_t baud = data[3]; // baudAndAirRate
uint8_t packet = data[4]; // packetSizeAndPower
uint8_t channel = data[5]; // channel
uint8_t worCycle = data[6]; // tranModeAndWorCycle
uint8_t baudField = baud & 0xE0; // bits 5,6,7 (baudrate)
Inicializar(baudField);
EnviarDadosCAN(MontarMensagemCAN(CanMessagePosicaoDados::Status));
if (Conectado) {
if (requisitarParametrosLoRa()) {
EnviarDadosCAN(MontarMensagemCAN(CanMessagePosicaoDados::Dados1));
Configurado =
parametrosAtual.address == data[3] &&
parametrosAtual.baudAndAirRate == data[4] &&
parametrosAtual.packetSizeAndPower == data[5] &&
parametrosAtual.channel == data[6] &&
parametrosAtual.tranModeAndWorCycle == data[7];
parametrosAtual.address == addr &&
parametrosAtual.baudAndAirRate == baud &&
parametrosAtual.packetSizeAndPower == packet &&
parametrosAtual.channel == channel &&
parametrosAtual.tranModeAndWorCycle == worCycle;
if (!Configurado) {
Configurado = configurarModuloLoRa(
data[3], // address
data[4], // baudAndAirRate
data[5], // packetSizeAndPower
data[6], // channel
data[7] // tranModeAndWorCycle
);
Configurado = configurarModuloLoRa(addr, baud, packet, channel, worCycle);
}
}
}

View File

@ -9,7 +9,7 @@ class Rele {
public:
static std::vector<uint8_t> ConfigurarRele(std::vector<Rele*>& lista, std::vector<uint8_t>& data, const String& Mod_ID);
static void ComandarRele(std::vector<Rele*>& lista, std::vector<uint8_t>& data, uint8_t& id);
static void ComandarRele(std::vector<Rele*>& lista, std::vector<uint8_t>& data);
Rele(String _modID, String _id) {
Mod_ID = _modID;
@ -88,8 +88,8 @@ class Rele {
std::vector<uint8_t> MontarMensagemCAN(CanMessagePosicaoDados posicao) {
std::vector<uint8_t> data;
data.push_back(ID_Num);
data.push_back(static_cast<uint8_t>(posicao));
data.push_back(ID_Num);
switch (posicao) {
case CanMessagePosicaoDados::Status: {
data.push_back(Iniciado ? 1 : 0);
@ -108,19 +108,19 @@ class Rele {
std::vector<uint8_t> Rele::ConfigurarRele(std::vector<Rele*>& lista, std::vector<uint8_t>& data, const String& Mod_ID) {
std::vector<uint8_t> status;
if (data.size() < 3) return status;
if (data.size() < 2) return status;
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[0];
uint8_t idNum = data[1];
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[2];
auto it = std::find_if(lista.begin(), lista.end(), [idNum](Rele* s) { return s->ID_Num == idNum; });
bool jaExiste = it != lista.end();
Rele* sensor;
switch (posicao) {
case CanMessagePosicaoDados::Config1: {
if (data.size() < 8) return status;
bool conectar = data[4] == 1;
bool atuacaoNivelAlto = data[5] == 1;
TiposBarramentos tipoBarramento = (TiposBarramentos)data[6];
int pino = data[7];
if (data.size() < 7) return status;
bool conectar = data[3] == 1;
bool atuacaoNivelAlto = data[4] == 1;
TiposBarramentos tipoBarramento = (TiposBarramentos)data[5];
int pino = data[6];
if (conectar) {
if (!jaExiste) {
sensor = new Rele(Mod_ID, "sRLE_" + String(idNum));
@ -155,11 +155,19 @@ std::vector<uint8_t> Rele::ConfigurarRele(std::vector<Rele*>& lista, std::vector
return status;
}
void Rele::ComandarRele(std::vector<Rele*>& lista, std::vector<uint8_t>& data, uint8_t& id) {
if (data.size() < 4) return;
void Rele::ComandarRele(std::vector<Rele*>& lista, std::vector<uint8_t>& data) {
if (data.size() < 3) return;
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[0];
uint8_t idNum = data[1];
for (auto* _rele : lista) {
if (_rele->ID_Num == id) {
_rele->AtualizarStatus((Estado)data[3]);
if (_rele->ID_Num == idNum) {
switch (posicao) {
case CanMessagePosicaoDados::Command1: {
Estado novoEstado = (Estado)data[2];
_rele->AtualizarStatus(novoEstado);
break;
}
}
return;
}
}

View File

@ -103,8 +103,8 @@ class SensorCorrente {
std::vector<uint8_t> MontarMensagemCAN(CanMessagePosicaoDados posicao) {
std::vector<uint8_t> data;
data.push_back(ID_Num);
data.push_back(static_cast<uint8_t>(posicao));
data.push_back(ID_Num);
switch (posicao) {
case CanMessagePosicaoDados::Status: {
@ -134,20 +134,20 @@ class SensorCorrente {
static std::vector<uint8_t> ConfigurarSensor(std::vector<SensorCorrente*>& lista, std::vector<uint8_t>& data, const String& Mod_ID) {
std::vector<uint8_t> status;
if (data.size() < 3) return status;
if (data.size() < 2) return status;
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[0];
uint8_t idNum = data[1];
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[2];
auto it = std::find_if(lista.begin(), lista.end(), [idNum](SensorCorrente* s) { return s->ID_Num == idNum; });
bool jaExiste = it != lista.end();
SensorCorrente* sensor;
switch (posicao) {
case CanMessagePosicaoDados::Config1: {
if (data.size() < 8) return status;
bool conectar = data[4] == 1;
uint8_t endereco = data[5];
TiposShuntCorrente aMax = (TiposShuntCorrente)data[6];
int canalMux = data[7];
if (data.size() < 7) return status;
bool conectar = data[3] == 1;
uint8_t endereco = data[4];
TiposShuntCorrente aMax = (TiposShuntCorrente)data[5];
int canalMux = data[6];
if (conectar) {
if (!jaExiste) {

View File

@ -93,8 +93,8 @@ class SensorFluxo {
std::vector<uint8_t> MontarMensagemCAN(CanMessagePosicaoDados posicao) {
std::vector<uint8_t> data;
data.push_back(ID_Num);
data.push_back(static_cast<uint8_t>(posicao));
data.push_back(ID_Num);
switch (posicao) {
case CanMessagePosicaoDados::Status: {
data.push_back(Iniciado ? 1 : 0);
@ -156,17 +156,17 @@ class SensorFluxo {
std::vector<uint8_t> SensorFluxo::ConfigurarSensor(std::vector<SensorFluxo*>& lista, std::vector<uint8_t>& data, const String& Mod_ID) {
std::vector<uint8_t> status;
if (data.size() < 3) return status;
uint8_t idNum = data[1];
if (data.size() < 2) return status;
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[2];
uint8_t idNum = data[1];
auto it = std::find_if(lista.begin(), lista.end(), [idNum](SensorFluxo* s) { return s->ID_Num == idNum; });
bool jaExiste = it != lista.end();
SensorFluxo* sensor;
switch (posicao) {
case CanMessagePosicaoDados::Config1: {
if (data.size() < 6) return status;
bool conectar = data[4] == 1;
int pino = data[5];
if (data.size() < 5) return status;
bool conectar = data[3] == 1;
int pino = data[4];
if (conectar) {
if (!jaExiste) {
sensor = new SensorFluxo(Mod_ID, "sFLX_" + String(idNum));

View File

@ -127,8 +127,8 @@ class SensorIMU {
std::vector<uint8_t> MontarMensagemCAN(CanMessagePosicaoDados posicao) {
std::vector<uint8_t> data;
data.push_back(ID_Num);
data.push_back(static_cast<uint8_t>(posicao));
data.push_back(ID_Num);
switch (posicao) {
case CanMessagePosicaoDados::Status: {
@ -277,18 +277,18 @@ class SensorIMU {
std::vector<uint8_t> SensorIMU::ConfigurarSensor(std::vector<SensorIMU*>& lista, std::vector<uint8_t>& data, const String& Mod_ID) {
std::vector<uint8_t> status;
if (data.size() < 3) return status;
if (data.size() < 2) return status;
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[0];
uint8_t idNum = data[1];
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[2];
auto it = std::find_if(lista.begin(), lista.end(), [idNum](SensorIMU* s) { return s->ID_Num == idNum; });
bool jaExiste = it != lista.end();
SensorIMU* sensor;
switch (posicao) {
case CanMessagePosicaoDados::Config1: {
if (data.size() < 7) return status;
bool conectar = data[4] == 1;
uint8_t enderecoMpu = data[5];
uint8_t enderecoBmp = data[6];
if (data.size() < 6) return status;
bool conectar = data[3] == 1;
uint8_t enderecoMpu = data[4];
uint8_t enderecoBmp = data[5];
if (conectar) {
if (!jaExiste) {
sensor = new SensorIMU(Mod_ID, "sIMU_" + String(idNum));

View File

@ -1,71 +0,0 @@
#include "SerialService.h"
#include "Pinout.h"
#include "Utils.h"
#include <MechaQMC5883.h>
#ifndef SensorMagnetometroModel
#define SensorMagnetometroModel
class SensorMagnetometro {
public:
SensorMagnetometro(String _modID, String _id, int _taxaAmostragem = 2000) {
Mod_ID = _modID;
_ID = _id;
}
// Variáveis
MechaQMC5883* qmc = new MechaQMC5883();
// Definições
String Mod_ID;
String _ID;
S_Code _componente = sMAG;
byte _Endereco;
bool Iniciado = false;
void Inicializar() {
if (Iniciado) {
//EnviarDadosSerial(_ID + " ja inicializado");
//EnviarDadosSerial(Mod_ID, MontarProtocoloSensor(sCFG, _ID, Iniciado ? "1" : "0"));
return;
}
qmc.init();
Iniciado = true;
//EnviarDadosSerial(Mod_ID, MontarProtocoloSensor(sCFG, _ID, Iniciado ? "1" : "0"));
}
void Desligar() {
if (!Iniciado) {
//EnviarDadosSerial(_ID + " nao esta inicializado");
//EnviarDadosSerial(Mod_ID, MontarProtocoloSensor(sCFG, _ID, Iniciado ? "1" : "0"));
return;
}
//EnviarDadosSerial(_ID + " Desligado");
Iniciado = false;
//EnviarDadosSerial(Mod_ID, MontarProtocoloSensor(sCFG, _ID, Iniciado ? "1" : "0"));
}
void AferirOrientacao() {
int x, y, z;
float orientacao;
qmc.read(&x, &y, &z,&orientacao);
}
void RequisitarDados() {
AferirOrientacao();
//EnviarDadosSerial(Mod_ID, MontarProtocoloSensor(sMAG, _ID, MontarDadosProtocoloMagnetometro(x, y, z, orientacao)));
}
};
#endif

View File

@ -76,8 +76,8 @@ class SensorMassa {
std::vector<uint8_t> MontarMensagemCAN(CanMessagePosicaoDados posicao) {
std::vector<uint8_t> data;
data.push_back(ID_Num);
data.push_back(static_cast<uint8_t>(posicao));
data.push_back(ID_Num);
switch (posicao) {
case CanMessagePosicaoDados::Status: {
data.push_back(Iniciado ? 1 : 0);
@ -119,20 +119,20 @@ class SensorMassa {
std::vector<uint8_t> SensorMassa::ConfigurarSensor(std::vector<SensorMassa*>& lista, std::vector<uint8_t>& data, const String& Mod_ID) {
std::vector<uint8_t> status;
if (data.size() < 3) return status;
if (data.size() < 2) return status;
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[0];
uint8_t idNum = data[1];
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[2];
auto it = std::find_if(lista.begin(), lista.end(), [idNum](SensorMassa* s) { return s->ID_Num == idNum; });
bool jaExiste = it != lista.end();
SensorMassa* sensor;
switch (posicao) {
case CanMessagePosicaoDados::Config1: {
if (data.size() < 7) return status;
bool conectar = data[4] == 1;
int pinoDt = data[5];
int pinoSck = data[6];
//uint16_t offsetInt = ((uint16_t)data[6] << 8) | data[7];
//float offset = offsetInt / 100.0;
if (data.size() < 8) return status;
bool conectar = data[3] == 1;
int pinoDt = data[4];
int pinoSck = data[5];
uint16_t offsetInt = ((uint16_t)data[6] << 8) | data[7];
float offset = offsetInt / 100.0;
if (conectar) {
if (!jaExiste) {
sensor = new SensorMassa(Mod_ID, "sMAS_" + String(idNum));
@ -144,7 +144,7 @@ std::vector<uint8_t> SensorMassa::ConfigurarSensor(std::vector<SensorMassa*>& li
sensor->ID_Num = idNum;
sensor->_pinoDT = PinoModel(pinoDt, CONTROLADOR, _INPUT, DIGITAL);
sensor->_pinoSCK = PinoModel(pinoSck, CONTROLADOR, _OUTPUT);
//sensor->_Offset = offset;
sensor->_Offset = offset;
sensor->Inicializar();
if (!jaExiste) {
lista.push_back(sensor);

View File

@ -72,8 +72,8 @@ class SensorPressao {
std::vector<uint8_t> MontarMensagemCAN(CanMessagePosicaoDados posicao) {
std::vector<uint8_t> data;
data.push_back(ID_Num);
data.push_back(static_cast<uint8_t>(posicao));
data.push_back(ID_Num);
switch (posicao) {
case CanMessagePosicaoDados::Status: {
data.push_back(Iniciado ? 1 : 0);
@ -107,17 +107,17 @@ class SensorPressao {
std::vector<uint8_t> SensorPressao::ConfigurarSensor(std::vector<SensorPressao*>& lista, std::vector<uint8_t>& data, const String& Mod_ID) {
std::vector<uint8_t> status;
if (data.size() < 3) return status;
if (data.size() < 2) return status;
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[0];
uint8_t idNum = data[1];
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[2];
auto it = std::find_if(lista.begin(), lista.end(), [idNum](SensorPressao* s) { return s->ID_Num == idNum; });
bool jaExiste = it != lista.end();
SensorPressao* sensor;
switch (posicao) {
case CanMessagePosicaoDados::Config1: {
if (data.size() < 6) return status;
bool conectar = data[4] == 1;
int pino = data[5];
if (data.size() < 5) return status;
bool conectar = data[3] == 1;
int pino = data[4];
if (conectar) {
if (!jaExiste) {
sensor = new SensorPressao(Mod_ID, "sPRS_" + String(idNum));

View File

@ -77,8 +77,8 @@ class SensorTemperatura {
std::vector<uint8_t> MontarMensagemCAN(CanMessagePosicaoDados posicao) {
std::vector<uint8_t> data;
data.push_back(ID_Num);
data.push_back(static_cast<uint8_t>(posicao));
data.push_back(ID_Num);
switch (posicao) {
case CanMessagePosicaoDados::Status: {
data.push_back(Iniciado ? 1 : 0);
@ -122,18 +122,18 @@ class SensorTemperatura {
std::vector<uint8_t> SensorTemperatura::ConfigurarSensor(std::vector<SensorTemperatura*>& lista, std::vector<uint8_t>& data, const String& Mod_ID) {
std::vector<uint8_t> status;
if (data.size() < 3) return status;
if (data.size() < 2) return status;
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[0];
uint8_t idNum = data[1];
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[2];
auto it = std::find_if(lista.begin(), lista.end(), [idNum](SensorTemperatura* s) { return s->ID_Num == idNum; });
bool jaExiste = it != lista.end();
SensorTemperatura* sensor;
switch (posicao) {
case CanMessagePosicaoDados::Config1: {
if (data.size() < 7) return status;
bool conectar = data[4] == 1;
TiposBarramentos tipoBarramento = (TiposBarramentos)data[5];
int pino = data[6];
if (data.size() < 6) return status;
bool conectar = data[3] == 1;
TiposBarramentos tipoBarramento = (TiposBarramentos)data[4];
int pino = data[5];
if (conectar) {
if (!jaExiste) {
sensor = new SensorTemperatura(Mod_ID, "sTMP_" + String(idNum));

View File

@ -10,7 +10,7 @@ class ServoFreio {
public:
static std::vector<uint8_t> ConfigurarServo(std::vector<ServoFreio*>& lista, std::vector<uint8_t>& data, const String& Mod_ID);
static void ComandarServo(std::vector<ServoFreio*>& lista, std::vector<uint8_t>& data, uint8_t& id);
static void ComandarServo(std::vector<ServoFreio*>& lista, std::vector<uint8_t>& data);
ServoFreio(String _modID, String _id) {
Mod_ID = _modID;
@ -81,8 +81,8 @@ class ServoFreio {
std::vector<uint8_t> MontarMensagemCAN(CanMessagePosicaoDados posicao) {
std::vector<uint8_t> data;
data.push_back(ID_Num);
data.push_back(static_cast<uint8_t>(posicao));
data.push_back(ID_Num);
switch (posicao) {
case CanMessagePosicaoDados::Status: {
data.push_back(Iniciado ? 1 : 0);
@ -101,19 +101,19 @@ class ServoFreio {
std::vector<uint8_t> ServoFreio::ConfigurarServo(std::vector<ServoFreio*>& lista, std::vector<uint8_t>& data, const String& Mod_ID) {
std::vector<uint8_t> status;
if (data.size() < 3) return status;
if (data.size() < 2) return status;
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[0];
uint8_t idNum = data[1];
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[2];
auto it = std::find_if(lista.begin(), lista.end(), [idNum](ServoFreio* s) { return s->ID_Num == idNum; });
bool jaExiste = it != lista.end();
ServoFreio* sensor;
switch (posicao) {
case CanMessagePosicaoDados::Config1: {
if (data.size() < 8) return status;
bool conectar = data[4] == 1;
bool incremental = data[5] == 1;
TiposBarramentos tipoBarramento = (TiposBarramentos)data[6];
int pino = data[7];
if (data.size() < 7) return status;
bool conectar = data[3] == 1;
bool incremental = data[4] == 1;
TiposBarramentos tipoBarramento = (TiposBarramentos)data[5];
int pino = data[6];
if (conectar) {
if (!jaExiste) {
sensor = new ServoFreio(Mod_ID, "sFRO_" + String(idNum));
@ -148,11 +148,19 @@ std::vector<uint8_t> ServoFreio::ConfigurarServo(std::vector<ServoFreio*>& lista
return status;
}
void ServoFreio::ComandarServo(std::vector<ServoFreio*>& lista, std::vector<uint8_t>& data, uint8_t& id) {
if (data.size() < 4) return;
void ServoFreio::ComandarServo(std::vector<ServoFreio*>& lista, std::vector<uint8_t>& data) {
if (data.size() < 3) return;
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[0];
uint8_t idNum = data[1];
for (auto* _freio : lista) {
if (_freio->ID_Num == id) {
_freio->AtualizarAngulo((int)data[3]);
if (_freio->ID_Num == idNum) {
switch (posicao) {
case CanMessagePosicaoDados::Command1: {
int novoAngulo = (int)data[2];
_freio->AtualizarAngulo(novoAngulo);
break;
}
}
return;
}
}

View File

@ -9,7 +9,7 @@ class Sinaleiro {
public:
static std::vector<uint8_t> ConfigurarSinaleiro(std::vector<Sinaleiro*>& lista, std::vector<uint8_t>& data, const String& Mod_ID);
static void ComandarSinaleiro(std::vector<Sinaleiro*>& lista, std::vector<uint8_t>& data, uint8_t& id);
static void ComandarSinaleiro(std::vector<Sinaleiro*>& lista, std::vector<uint8_t>& data);
Sinaleiro(String _modID, String _id, int _taxaAmostragem = 2000) {
Mod_ID = _modID;
@ -77,8 +77,8 @@ class Sinaleiro {
std::vector<uint8_t> MontarMensagemCAN(CanMessagePosicaoDados posicao) {
std::vector<uint8_t> data;
data.push_back(ID_Num);
data.push_back(static_cast<uint8_t>(posicao));
data.push_back(ID_Num);
switch (posicao) {
case CanMessagePosicaoDados::Status: {
data.push_back(Iniciado ? 1 : 0);
@ -145,18 +145,18 @@ class Sinaleiro {
std::vector<uint8_t> Sinaleiro::ConfigurarSinaleiro(std::vector<Sinaleiro*>& lista, std::vector<uint8_t>& data, const String& Mod_ID) {
std::vector<uint8_t> status;
if (data.size() < 3) return status;
if (data.size() < 2) return status;
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[0];
uint8_t idNum = data[1];
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[2];
auto it = std::find_if(lista.begin(), lista.end(), [idNum](Sinaleiro* s) { return s->ID_Num == idNum; });
bool jaExiste = it != lista.end();
Sinaleiro* sensor;
switch (posicao) {
case CanMessagePosicaoDados::Config1: {
if (data.size() < 7) return status;
bool conectar = data[4] == 1;
TiposBarramentos tipoBarramento = (TiposBarramentos)data[5];
int pino = data[6];
if (data.size() < 6) return status;
bool conectar = data[3] == 1;
TiposBarramentos tipoBarramento = (TiposBarramentos)data[4];
int pino = data[5];
if (conectar) {
if (!jaExiste) {
sensor = new Sinaleiro(Mod_ID, "sLED_" + String(idNum));
@ -190,14 +190,25 @@ std::vector<uint8_t> Sinaleiro::ConfigurarSinaleiro(std::vector<Sinaleiro*>& lis
return status;
}
void Sinaleiro::ComandarSinaleiro(std::vector<Sinaleiro*>& lista, std::vector<uint8_t>& data, uint8_t& id) {
if (data.size() < 7) return;
void Sinaleiro::ComandarSinaleiro(std::vector<Sinaleiro*>& lista, std::vector<uint8_t>& data) {
if (data.size() < 6) return;
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[0];
uint8_t idNum = data[1];
for (auto* _led : lista) {
if (_led->ID_Num == id) {
_led->_Status = (StatusLED)data[3];
_led->_Qtd = data[4];
_led->_TempoMs = (uint16_t)data[5] * 10;
_led->_PausaMs = (uint16_t)data[6] * 10;
if (_led->ID_Num == idNum) {
switch (posicao) {
case CanMessagePosicaoDados::Command1: {
StatusLED novoStatus = (StatusLED)data[2];
int novaQtd = data[3];
uint16_t novoTempo = (uint16_t)data[4] * 10;
uint16_t novaPausa = (uint16_t)data[5] * 10;
_led->_Status = novoStatus;
_led->_Qtd = novaQtd;
_led->_TempoMs = novoTempo;
_led->_PausaMs = novaPausa;
break;
}
}
return;
}
}

View File

@ -60,14 +60,14 @@ void setup() {
inicializarDependenciasI2C();
// Registrar callback para processar mensagens CAN recebidas
canService.setReceiveCallback([](int packetSize, int senderId, byte funcCode, byte* data, int dataLength) {
canService.setReceiveCallback([](int packetSize, int senderId, CanMessagePosicaoDados posicao, byte* data, int dataLength) {
std::vector<uint8_t> fullData;
fullData.push_back(funcCode); // Primeiro byte é sempre o funcCode
fullData.push_back(static_cast<uint8_t>(posicao)); // Primeiro byte é sempre a posicao
for (int i = 0; i < dataLength; i++) {
fullData.push_back(data[i]);
}
ProcessarFrameCAN(fullData);
ProcessarFrameCAN(posicao, fullData);
});
canService.begin();
@ -95,21 +95,27 @@ void enviarLogsPeriodicamente() {
}
void enviarDadosSensores(int id_num, CanMessagePosicaoDados posicao) {
if (Conectado || posicao == CanMessagePosicaoDados::Status) {
unsigned long startLoop = millis();
if (Conectado) {
PrintTela("Atualizando dados dos sensores...");
bool enviarStatus = qtdEnviosStatus >= maxEnviosStatus && posicao != CanMessagePosicaoDados::Status;
bool todosDados = posicao == CanMessagePosicaoDados::DadosAll;
bool todosIDs = id_num == canService.ID_Num_sTOD;
if (id_num == canService.ID_Num_sMOD) {
EnviarDadosCAN(canService.MontarFrameReqStatusMod(D_Code, Conectado, VERSION));
return;
}
if (id_num == canService.ID_Num_sLRA) {
EnviarDadosCAN(loraService.MontarMensagemCAN(posicao));
return;
}
PrintTela("Atualizando dados dos sensores...");
if (todosIDs && enviarStatus) {
ProcessarChk();
EnviarDadosCAN(canService.MontarFrameReqStatusMod(D_Code, Conectado, VERSION));
EnviarDadosCAN(loraService.MontarMensagemCAN(CanMessagePosicaoDados::Status));
}
@ -225,9 +231,13 @@ void enviarDadosSensores(int id_num, CanMessagePosicaoDados posicao) {
else {
qtdEnviosStatus++;
}
}
latenciaLoop = millis() - startLoop;
if (posicao == CanMessagePosicaoDados::DadosAll) {
EnviarDadosCAN(canService.MontarFrameReqDadosFim(latenciaLoop));
}
}
}
void EnviarDadosCAN(std::vector<uint8_t> data) {
@ -236,62 +246,58 @@ void EnviarDadosCAN(std::vector<uint8_t> data) {
}
}
void ProcessarFrameCAN(std::vector<uint8_t> data) {
void ProcessarFrameCAN(CanMessagePosicaoDados posicao, std::vector<uint8_t> data) {
if (data.size() < 1) return;
F_Code funcao = (F_Code)data[0];
F_Code funcao = canService.FuncaoPorPosicao(posicao);
switch (funcao) {
case F_Code::ChkTx: ProcessarChk(); break;
case F_Code::ReqTx: ProcessarReq(data); break;
case F_Code::CmdTx: ProcessarCmd(data); break;
case F_Code::CfgTx: ProcessarCfg(data); break;
}
}
void ProcessarChk() {
std::vector<uint8_t> data = canService.MontarFrameChk(D_Code, Conectado, VERSION);
EnviarDadosCAN(data);
}
void ProcessarReq(std::vector<uint8_t> data) {
if (data.size() < 3) return;
if (data.size() < 2) return;
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[0];
uint8_t id = data[1];
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[2];
enviarDadosSensores(id, posicao);
}
void ProcessarCfg(std::vector<uint8_t> data) {
if (data.size() < 4) return;
std::vector<uint8_t> _chkRx;
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[0];
uint8_t id = data[1];
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[2];
S_Code componente = DetectarComponente(id);
if (componente == S_Code::sMOD) {
switch (posicao) {
case CanMessagePosicaoDados::Config1: {
if (data.size() < 8) return;
bool conectar = data[4] == 1;
int taxa = data[5] * 10;
bool requisitar = data[6] == 1;
loraService.AddressBase = data[7];
bool conectar = data[2] == 1;
int taxa = data[3] * 10;
bool requisitar = data[4] == 1;
loraService.AddressBase = data[5];
int pinoSDA = data[6];
int pinoSCL = data[7];
_TaxaAmostragem = taxa;
RequisitarDados = requisitar;
Conectar = conectar;
break;
}
case CanMessagePosicaoDados::Config2: {
if (data.size() < 6) return;
int pinoSDA = data[4];
int pinoSCL = data[5];
LimparListasComponentes();
if (pinoSDA != PINO_INVALIDO && pinoSCL != PINO_INVALIDO) {
I2CService::DefinirPinos(pinoSDA, pinoSCL);
if (I2CService::DefinirPinos(pinoSDA, pinoSCL) || !I2CService::I2CIniciado) {
inicializarDependenciasI2C();
}
}
vTaskDelay(pdMS_TO_TICKS(100));
Conectado = Conectar;
_chkRx = canService.MontarFrameChk(D_Code, Conectado, VERSION);
LimparListasComponentes();
Conectado = conectar;
_chkRx = canService.MontarFrameReqStatusMod(D_Code, Conectado, VERSION);
PrintTela("[SEN] Configuracao do modulo concluida");
break;
}
@ -301,7 +307,7 @@ void ProcessarCfg(std::vector<uint8_t> data) {
_chkRx = loraService.ConfigurarModulo(data);
}
else {
componente = (S_Code)data[3];
componente = (S_Code)data[2];
switch (componente) {
case sTMP: {
_chkRx = SensorTemperatura::ConfigurarSensor(listaSensoresTemperatura, data, Mod_ID);
@ -335,21 +341,21 @@ void ProcessarCfg(std::vector<uint8_t> data) {
}
void ProcessarCmd(std::vector<uint8_t> data) {
if (data.size() < 3) return;
if (data.size() < 2) return;
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[0];
uint8_t id = data[1];
CanMessagePosicaoDados posicao = (CanMessagePosicaoDados)data[2];
S_Code componente = DetectarComponente(id);
switch (componente) {
case sLED: {
Sinaleiro::ComandarSinaleiro(listaSinaleiros, data, id);
Sinaleiro::ComandarSinaleiro(listaSinaleiros, data);
break;
}
case sRLE: {
Rele::ComandarRele(listaReles, data, id);
Rele::ComandarRele(listaReles, data);
break;
}
case sFRO: {
ServoFreio::ComandarServo(listaServoFreios, data, id);
ServoFreio::ComandarServo(listaServoFreios, data);
break;
}
case sLRA: {