agrobot_base/AgroBase/OperationControl/ViewModels/Windows/DockWindowViewModel.cs

1419 lines
61 KiB
C#

using AgroBase.Models;
using AgroBase.Models.Operacoes;
using AgroBase.Services;
using Newtonsoft.Json.Linq;
using OperationControl.Controls;
using OperationControl.Helpers;
using OperationControl.Models;
using OperationControl.ViewModels.Views.Operacao;
using OperationControl.Views;
using OperationControl.Views.Operacao;
using System.ComponentModel;
using System.Windows;
using System.Windows.Input;
using static AgroBase.Models.Enums;
using static OperationControl.Services.BaseFixService;
namespace OperationControl.ViewModels
{
public class DockWindowViewModel : INotifyPropertyChanged
{
private readonly ConfigConexaoView _viewConfig;
private readonly PreparacaoMapaView _viewPreparacaoMapa;
public readonly PreparacaoMapaTopView _viewPreparacaoMapaTop;
public readonly PreparacaoMapaBottomView _viewPreparacaoMapaBottom;
private readonly OperacaoTopView _viewOperacaoTop;
public readonly OperacaoCenterView _viewOperacaoCenter;
public readonly OperacaoLeftView _viewOperacaoLeft;
public readonly OperacaoRightView _viewOperacaoRight;
public readonly OperacaoBottomView _viewOperacaoBottom;
public OperacaoBottomViewModel BottomVM => _viewOperacaoBottom?._vm;
private DockStep _currentStep;
public DockWindowViewModel()
{
// Views
_viewConfig = new ConfigConexaoView();
_viewConfig._vm.TudoOkChanged += OnTudoOkChanged;
_viewPreparacaoMapa = new PreparacaoMapaView();
_viewPreparacaoMapaTop = new PreparacaoMapaTopView();
_viewPreparacaoMapaBottom = new PreparacaoMapaBottomView();
_viewPreparacaoMapaBottom._vm.CarregarMapaSolicitado += OnCarregarMapaSolicitado;
_viewPreparacaoMapaBottom._vm.FixarBaseSolicitado += OnFixarBaseSolicitado;
_viewPreparacaoMapaBottom._vm.AplicarOffsetSolicitado += OnAplicarOffsetSolicitado;
_viewOperacaoTop = new OperacaoTopView();
_viewOperacaoCenter = new OperacaoCenterView();
_viewOperacaoCenter._vm.RoverSelecionadoChanged += OnRoverSelecionadoChanged;
_viewOperacaoLeft = new OperacaoLeftView();
_viewOperacaoRight = new OperacaoRightView();
_viewOperacaoRight._vm.PropertyChanged += OperacaoRightVm_PropertyChanged;
_viewOperacaoRight._vm.RoverSelecionadoChanged += OnRoverSelecionadoChanged;
_viewOperacaoRight._vm.SecaoSelecionadaChanged += OnSecaoSelecionadaChanged;
_viewOperacaoRight.areaParametrizacao._vm.LerParametrosSolicitado += OnLerParametrosSolicitado;
_viewOperacaoRight.areaParametrizacao._vm.SalvarParametrosSolicitado += OnSalvarParametrosSolicitado;
_viewOperacaoBottom = new OperacaoBottomView();
_viewOperacaoBottom._vm.SolicitarAbrirDiagnostico += AbrirDiagnosticoPeloAlerta;
// Commands
BackCommand = new RelayCommand(_ => GoBack(), _ => CanGoBack);
NextCommand = new RelayCommand(_ => GoNext(), _ => CanGoNext);
// Estado inicial
ConfigConexaoOk = _viewConfig._vm.TudoOk;
CurrentStep = DockStep.ConfigConexao;
}
private void OnTudoOkChanged(bool ok)
{
ConfigConexaoOk = ok;
OnPropertyChanged(nameof(CanGoNext));
CommandManager.InvalidateRequerySuggested();
}
// ====== ETAPA ATUAL ======
public ModoOperacao ModoOperacaoAtual => _viewConfig._vm.TipoOperacaoSelecionado;
public DockStep CurrentStep
{
get => _currentStep;
set
{
if (_currentStep != value)
{
_currentStep = value;
OnPropertyChanged(nameof(CurrentStep));
OnPropertyChanged(nameof(CanGoBack));
OnPropertyChanged(nameof(CanGoNext));
OnPropertyChanged(nameof(MostrarPainelEsquerdo));
OnPropertyChanged(nameof(MostrarBotaoVoltarEsquerda));
OnPropertyChanged(nameof(RightPanelWidth));
OnPropertyChanged(nameof(LeftPanelWidth));
AtualizarConteudo();
CommandManager.InvalidateRequerySuggested();
}
}
}
// ====== ESTADO ======
private bool _configConexaoOk;
public bool ConfigConexaoOk
{
get => _configConexaoOk;
set
{
if (_configConexaoOk != value)
{
_configConexaoOk = value;
OnPropertyChanged(nameof(ConfigConexaoOk));
OnPropertyChanged(nameof(CanGoNext));
CommandManager.InvalidateRequerySuggested();
}
}
}
private bool _mapaCarregado;
public bool MapaCarregado
{
get => _mapaCarregado;
set
{
if (_mapaCarregado != value)
{
_mapaCarregado = value;
OnPropertyChanged(nameof(MapaCarregado));
OnPropertyChanged(nameof(CanGoNext));
CommandManager.InvalidateRequerySuggested();
}
}
}
private bool _baseFixada = AppShell.Mock;
public bool BaseFixada
{
get => _baseFixada;
set
{
if (_baseFixada != value)
{
_baseFixada = value;
OnPropertyChanged(nameof(BaseFixada));
OnPropertyChanged(nameof(CanGoNext));
CommandManager.InvalidateRequerySuggested();
}
}
}
public bool CanGoBack => CurrentStep != DockStep.ConfigConexao;
public bool CanGoNext
{
get
{
return CurrentStep switch
{
DockStep.ConfigConexao => PodeAvancarConfigConexao(),
DockStep.PreparacaoMapa => MapaCarregado && BaseFixada,
_ => false
};
}
}
private bool PodeAvancarConfigConexao()
{
return ModoOperacaoAtual switch
{
ModoOperacao.Automatico => _viewConfig._vm.RedeOk && _viewConfig._vm.GnssOk,
ModoOperacao.Manual => _viewConfig._vm.RedeOk,
_ => false
};
}
public bool MostrarPainelEsquerdo => CurrentStep == DockStep.ParametrizacaoRover;
public bool MostrarBotaoVoltarEsquerda => CurrentStep != DockStep.ParametrizacaoRover;
public GridLength LeftPanelWidth
{
get
{
return CurrentStep switch
{
DockStep.ParametrizacaoRover => new GridLength(280),
_ => new GridLength(60)
};
}
}
public GridLength RightPanelWidth
{
get
{
return CurrentStep switch
{
DockStep.ParametrizacaoRover => _viewOperacaoRight?._vm?.IsCollapsed == true
? new GridLength(44)
: new GridLength(320),
_ => new GridLength(60)
};
}
}
private void OperacaoRightVm_PropertyChanged(object sender, PropertyChangedEventArgs e)
{
if (e.PropertyName == nameof(OperacaoRightViewModel.IsCollapsed))
{
OnPropertyChanged(nameof(RightPanelWidth));
}
}
// ====== CONTEÚDOS ======
private object _centerContent;
public object CenterContent
{
get => _centerContent;
set
{
_centerContent = value;
OnPropertyChanged(nameof(CenterContent));
}
}
private object _topContent;
public object TopContent
{
get => _topContent;
set
{
_topContent = value;
OnPropertyChanged(nameof(TopContent));
}
}
private object _bottomContent;
public object BottomContent
{
get => _bottomContent;
set
{
_bottomContent = value;
OnPropertyChanged(nameof(BottomContent));
}
}
private object _leftContent;
public object LeftContent
{
get => _leftContent;
set
{
_leftContent = value;
OnPropertyChanged(nameof(LeftContent));
}
}
private object _rightContent;
public object RightContent
{
get => _rightContent;
set
{
_rightContent = value;
OnPropertyChanged(nameof(RightContent));
}
}
// ====== COMMANDS ======
public ICommand BackCommand { get; }
public ICommand NextCommand { get; }
private void GoBack()
{
switch (CurrentStep)
{
case DockStep.PreparacaoMapa:
CurrentStep = DockStep.ConfigConexao;
break;
}
}
private void GoNext()
{
if (!CanGoNext) return;
switch (CurrentStep)
{
case DockStep.ConfigConexao:
if (ModoOperacaoAtual == ModoOperacao.Manual)
CurrentStep = DockStep.ParametrizacaoRover;
else
CurrentStep = DockStep.PreparacaoMapa;
break;
case DockStep.PreparacaoMapa:
CurrentStep = DockStep.ParametrizacaoRover;
break;
}
}
private FrameworkElement CriarBotaoNextSimples()
{
return new System.Windows.Controls.Button
{
Content = "⮞",
FontSize = 24,
Width = 40,
Height = 40,
HorizontalAlignment = System.Windows.HorizontalAlignment.Center,
VerticalAlignment = VerticalAlignment.Center,
Command = NextCommand
};
}
private void AtualizarConteudo()
{
TopContent = null;
BottomContent = null;
LeftContent = null;
RightContent = null;
CenterContent = null;
switch (CurrentStep)
{
case DockStep.ConfigConexao:
CenterContent = _viewConfig;
RightContent = CriarBotaoNextSimples();
break;
case DockStep.PreparacaoMapa:
TopContent = _viewPreparacaoMapaTop;
CenterContent = _viewPreparacaoMapa;
BottomContent = _viewPreparacaoMapaBottom;
RightContent = CriarBotaoNextSimples();
break;
case DockStep.ParametrizacaoRover:
TopContent = _viewOperacaoTop;
LeftContent = _viewOperacaoLeft;
CenterContent = _viewOperacaoCenter;
RightContent = _viewOperacaoRight;
BottomContent = _viewOperacaoBottom;
AtualizarDadosMapa(null);
AtualizarBarraSuperior(StatusModulo.Conectado, "BASE", "VISÃO GERAL", "Selecione um equipamento na lista à direita para configurá-lo", "NORMAL", "Aguardando");
break;
}
OnPropertyChanged(nameof(MostrarPainelEsquerdo));
OnPropertyChanged(nameof(MostrarBotaoVoltarEsquerda));
}
// ====== INotifyPropertyChanged ======
public event PropertyChangedEventHandler PropertyChanged;
private void OnPropertyChanged(string nome)
{
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(nome));
}
public void AtualizarBarraSuperior(OperacaoParametrosModel rover)
{
var obj = rover?.DadosLeitura;
if (rover == null || obj == null)
return;
if (rover.RoverId != VariaveisControleOperacao.SelectedRoverId)
return;
var eventos = new List<MotivoTopBarModel>();
double tempoSemResposta = (DateTime.Now - rover.UltimoContato).TotalSeconds;
bool semComunicacao = !AppShell.Mock && tempoSemResposta >= VariaveisControleOperacao.TempoRoverVivo;
// ============================
// 0) Perda de comunicação
// ============================
if (semComunicacao)
{
eventos.Add(new MotivoTopBarModel
{
Prioridade = 2000,
Fonte = "Comunicacao",
Titulo = "PERDA DE COMUNICAÇÃO COM O ROVER",
Descricao = $"Sem resposta do rover há {tempoSemResposta:F1} s. Tentando reconectar automaticamente.",
StatusVisual = StatusModulo.Desconectado
});
}
// ============================
// 0) NCP desconectado
// ============================
if (obj.ModulosSaude?.All(x => (x?.status ?? StatusModulo.Desconectado) == StatusModulo.Desconectado) ?? false)
{
eventos.Add(new MotivoTopBarModel
{
Prioridade = 1100,
Fonte = "NCP",
Titulo = "NÚCLEO CENTRAL DE PROCESSAMENTO DESCONECTADO",
Descricao = "O núcleo central de processamento foi desconectado, tentando reconectar...",
StatusVisual = StatusModulo.Falha
});
}
// ============================
// 1) Emergência
// ============================
if (obj.Operacao?.Emergencia == true)
{
eventos.Add(new MotivoTopBarModel
{
Prioridade = 1000,
Fonte = "Emergencia",
Titulo = "OPERAÇÃO BLOQUEADA POR EMERGÊNCIA",
Descricao = "Parada de emergência solicitada.",
StatusVisual = StatusModulo.Falha
});
}
// ============================
// 2) Pausa
// ============================
if (obj.Operacao?.Pausa == true)
{
eventos.Add(new MotivoTopBarModel
{
Prioridade = 900,
Fonte = "Pausa",
Titulo = "OPERAÇÃO PAUSADA",
Descricao = "Pausa operacional solicitada.",
StatusVisual = StatusModulo.Alerta
});
}
// ============================
// 3) Controle
// ============================
var motivosControle = obj.Controle?.Motivos?
.Where(x => !string.IsNullOrWhiteSpace(x))
.Distinct()
.ToList() ?? new List<string>();
foreach (var motivo in motivosControle)
{
eventos.Add(new MotivoTopBarModel
{
Prioridade = 800,
Fonte = "Controle",
Titulo = "CONTROLE SEM LIBERAÇÃO",
Descricao = motivo,
StatusVisual = StatusModulo.Alerta
});
}
// ============================
// 4) Trajetória / autonomia
// ============================
var motivosTrajetoria = obj.Trajetoria?.AutonomiaCorredor?.Motivos?
.Where(x => !string.IsNullOrWhiteSpace(x))
.Distinct()
.ToList() ?? new List<string>();
foreach (var motivo in motivosTrajetoria)
{
eventos.Add(new MotivoTopBarModel
{
Prioridade = 700,
Fonte = "Trajetoria",
Titulo = "TRAJETÓRIA BLOQUEADA",
Descricao = motivo,
StatusVisual = StatusModulo.Alerta
});
}
// ============================
// 5) Módulos com condições operacionais críticas
// ============================
var modulosCriticos = obj.ModulosSaude?
.Where(mod =>
(mod?.condicoes_operacionais?.Any(cond => cond?.severidade > 90) ?? false) ||
(
!new List<StatusModulo>() { StatusModulo.Operante, StatusModulo.Alerta }.Contains(mod?.status ?? StatusModulo.Desconectado) &&
(rover?.ModulosMandatorios?.Any(x =>
(x?.Dispositivo ?? T_Code.Vzo) == (mod?.modulo ?? T_Code.Vzo) &&
(x?.Utilizar ?? false) &&
(x?.Mandatorio ?? false)
) ?? false)
) ||
(
(mod?.status ?? StatusModulo.Desconectado) == StatusModulo.Alerta &&
(rover?.ModulosMandatorios?.Any(x =>
(x?.Dispositivo ?? T_Code.Vzo) == (mod?.modulo ?? T_Code.Vzo) &&
(x?.Utilizar ?? false) &&
(x?.Mandatorio ?? false)
) ?? false)
)
)
.ToList() ?? new List<AgroBase.Models.Operadores.ManagerWorkerMessageResponseModulosPendentesModel>();
foreach (var modulo in modulosCriticos)
{
var nomeModulo = (modulo?.modulo ?? T_Code.Vzo).ToString();
bool temCondicaoSevera = modulo?.condicoes_operacionais?.Any(cond => cond?.severidade > 90) ?? false;
bool moduloMandatorioNaoOperante =
!new List<StatusModulo>() { StatusModulo.Operante, StatusModulo.Alerta }.Contains(modulo?.status ?? StatusModulo.Desconectado) &&
(rover?.ModulosMandatorios?.Any(x =>
(x?.Dispositivo ?? T_Code.Vzo) == (modulo?.modulo ?? T_Code.Vzo) &&
(x?.Utilizar ?? false) &&
(x?.Mandatorio ?? false)
) ?? false);
bool moduloMandatorioAlerta =
(modulo?.status ?? StatusModulo.Desconectado) == StatusModulo.Alerta &&
(rover?.ModulosMandatorios?.Any(x =>
(x?.Dispositivo ?? T_Code.Vzo) == (modulo?.modulo ?? T_Code.Vzo) &&
(x?.Utilizar ?? false) &&
(x?.Mandatorio ?? false)
) ?? false);
// Caso 1: módulo mandatório não operante
if (moduloMandatorioNaoOperante)
{
var statusTexto = (modulo?.status ?? StatusModulo.Desconectado).ToString();
string motivos = string.Join("; ", modulo?.motivos ?? new List<string>() { "Desconhecido" });
eventos.Add(new MotivoTopBarModel
{
Prioridade = 620,
Fonte = "ModuloCritico",
Titulo = "MÓDULO MANDATÓRIO NÃO OPERACIONAL",
Descricao = $"{nomeModulo}: módulo mandatório em estado '{statusTexto}': {motivos}",
StatusVisual = StatusModulo.Falha,
Modulo = modulo?.modulo
});
}
// Caso 2: condições operacionais severas
if (temCondicaoSevera)
{
var descricoesCriticas = modulo?.condicoes_operacionais?
.Where(cond => cond?.severidade > 90)
.Select(cond => cond?.descricao ?? "")
.Where(desc => !string.IsNullOrWhiteSpace(desc))
.Distinct()
.ToList() ?? new List<string>();
foreach (var desc in descricoesCriticas)
{
eventos.Add(new MotivoTopBarModel
{
Prioridade = 610,
Fonte = "ModuloCritico",
Titulo = "CONDIÇÕES OPERACIONAIS CRÍTICAS",
Descricao = $"{nomeModulo}: {desc}",
StatusVisual = StatusModulo.Alerta,
Modulo = modulo?.modulo
});
}
}
// Caso 3: módulo mandatório em alerta
if (moduloMandatorioAlerta)
{
var statusTexto = (modulo?.status ?? StatusModulo.Desconectado).ToString();
string motivos = string.Join("; ", modulo?.motivos ?? new List<string>() { "Desconhecido" });
eventos.Add(new MotivoTopBarModel
{
Prioridade = 600,
Fonte = "ModuloCritico",
Titulo = "MÓDULO MANDATÓRIO EM ALERTA",
Descricao = $"{nomeModulo}: módulo mandatório em estado '{statusTexto}': {motivos}",
StatusVisual = StatusModulo.Alerta,
Modulo = modulo?.modulo
});
}
}
var ordemModulos = new Dictionary<T_Code, int>
{
{ T_Code.Ipb, 1 },
{ T_Code.Npc, 2 },
{ T_Code.Can, 3 },
{ T_Code.Bat, 4 },
{ T_Code.Gps, 5 },
{ T_Code.Atu, 6 },
{ T_Code.Sen, 7 }
};
// ============================
// 6) Remove vazios / repetidos
// ============================
var eventosOrdenados = eventos
.Where(x => !string.IsNullOrWhiteSpace(x.Titulo) && !string.IsNullOrWhiteSpace(x.Descricao))
.GroupBy(x => new { x.Fonte, x.Titulo, x.Descricao, x.Prioridade, x.StatusVisual })
.Select(g => g.First())
.OrderByDescending(x => x.Prioridade)
.ThenBy(x => x.Modulo.HasValue && ordemModulos.ContainsKey(x.Modulo.Value)? ordemModulos[x.Modulo.Value] : int.MaxValue)
.ThenBy(x => x.Fonte)
.ToList();
if (!eventosOrdenados.Any())
{
eventosOrdenados.Add(new MotivoTopBarModel
{
Prioridade = 0,
Fonte = "Normal",
Titulo = "ROVER OPERANDO NORMALMENTE",
Descricao = "Trajetória, controle e operação em condição normal.",
StatusVisual = obj.StatusRover == StatusModulo.Desconectado
? StatusModulo.Desconectado
: StatusModulo.Operante
});
}
// ============================
// 7) Monta visual final
// ============================
StatusModulo statusVisual;
string linha1;
string linha2;
string badge;
string resumo;
if (eventosOrdenados.Any())
{
var principal = eventosOrdenados.First();
statusVisual = principal.StatusVisual;
linha1 = principal.Titulo;
// Pega até 3 descrições distintas, por prioridade
var descricoes = eventosOrdenados
.Select(x => x.Descricao?.Trim())
.Where(x => !string.IsNullOrWhiteSpace(x))
.Distinct()
.Take(3)
.ToList();
linha2 = string.Join(" • ", descricoes);
// Badge curto
badge = principal.Fonte switch
{
"Comunicacao" => "DESCONECTADO",
"Emergencia" => "EMERGÊNCIA",
"Pausa" => "PAUSADO",
"Trajetoria" => "TRAJETÓRIA",
"Controle" => "CONTROLE",
"ModuloCritico" => "ALERTA",
_ => statusVisual.ToString().ToUpper()
};
// Resumo curto
resumo = principal.Fonte switch
{
"Comunicacao" => "Sem telemetria",
"Emergencia" => "Parada imediata",
"Pausa" => "Aguardando retomada",
"Trajetoria" => "Operação bloqueada",
"Controle" => "Controle bloqueado",
"ModuloCritico" => "Atenção operacional",
_ => (obj.Operacao?.Status ?? StatusOperacao.NaoIniciado).ToString()
};
}
else
{
statusVisual = obj.StatusRover == StatusModulo.Desconectado
? StatusModulo.Desconectado
: StatusModulo.Operante;
linha1 = "ROVER OPERANDO NORMALMENTE";
linha2 = "Trajetória, controle e operação em condição normal.";
badge = statusVisual.ToString().ToUpper();
resumo = (obj.Operacao?.Status ?? StatusOperacao.NaoIniciado).ToString();
}
_viewOperacaoCenter?.Historico?._vm?.CompararERegistrarMudancasEventos(rover.RoverId, eventosOrdenados);
// Segurança extra: evita linha vazia
if (string.IsNullOrWhiteSpace(linha2))
linha2 = "Sem detalhes adicionais.";
// ============================
// 8) Atualiza UI
// ============================
System.Windows.Application.Current.Dispatcher.BeginInvoke(new Action(() =>
{
_viewOperacaoTop?._vm?.AtualizarStatus(
statusVisual,
rover.RoverId,
obj?.Operacao?.Status ?? StatusOperacao.NaoIniciado,
linha1,
linha2,
badge,
resumo
);
}));
}
public void AtualizarBarraSuperior(StatusModulo status, string titulo, string linha1, string linha2, string status_str, string resumo)
{
System.Windows.Application.Current.Dispatcher.BeginInvoke(new Action(() =>
{
_viewOperacaoTop?._vm?.AtualizarStatus(status, titulo, StatusOperacao.Parametrizando, linha1, linha2.Replace("\n\n", " • "), status_str, resumo);
}));
}
public void AtualizarDadosGnss(AgroBase.Models.GPSModel dados)
{
var bf = Models.Variaveis.GpsService.BaseFix;
if (bf.CorrecaoEmAndamento)
{
AtualizarProgressoFixacaoBase(bf.Progresso, bf.ProgressoStr);
if (bf.Progresso >= 100) FinalizarFixacaoBase(true, bf.ProgressoStr);
}
MapViewControl? Mapa = CurrentStep == DockStep.PreparacaoMapa ? _viewPreparacaoMapa?.MapaPreparacao : CurrentStep == DockStep.ParametrizacaoRover ? _viewOperacaoCenter?.Mapa : null;
if (CurrentStep == DockStep.PreparacaoMapa)
{
_viewPreparacaoMapaTop?._vm?.AtualizarDados(dados);
}
CriarMarcadorBase(Mapa);
Mapa?.markers?.UpdateMarkerPosition(VariaveisControleOperacao.BaseMarkerID, lat: dados?.Latitude, lon: dados?.Longitude, heading: dados?.OrientacaoReal, rawGnssLat: dados?.LatitudeAnt, rawGnssLon: dados?.LongitudeAnt);
}
public void AtualizarParametrosRover(OperacaoParametrosModel? rover)
{
_viewOperacaoRight?.areaParametrizacao?._vm?.AtualizarParametros(rover);
AtualizarDadosMapa(rover);
AtualizarDadosTela(rover);
}
public void AtualizarDadosMapa(OperacaoParametrosModel? dados)
{
_viewOperacaoCenter?.Mapa?.LoadMapFile(_ultimoMapaCarregado, _ultimoTipoMapaCarregado);
_viewOperacaoCenter?.Mapa?.CarregarDadosMapa(dados?.Mapa, dados?.RuasPercorrer, dados?.PontosRetorno);
}
#region TELA 2
private string? _ultimoMapaCarregado;
private TipoMapaOperacao _ultimoTipoMapaCarregado = TipoMapaOperacao.RuasPlantacao;
private void CriarMarcadorBase(MapViewControl Mapa)
{
string markerId = VariaveisControleOperacao.BaseMarkerID;
if (!Mapa?.markers?.Added(markerId) ?? false)
{
Mapa?.markers?.AddMarker(
markerId,
true,
lat: Models.Variaveis.GpsService?.UltimaLeitura?.Latitude,
lon: Models.Variaveis.GpsService?.UltimaLeitura?.Longitude,
heading: Models.Variaveis.GpsService?.UltimaLeitura?.OrientacaoReal,
label: "Base"
);
}
}
private void OnCarregarMapaSolicitado(string caminhoArquivo, TipoMapaOperacao tipo)
{
try
{
_ultimoMapaCarregado = caminhoArquivo;
_viewPreparacaoMapa?.MapaPreparacao?.LoadMapFile(caminhoArquivo, tipo);
MapaCarregado = true;
_viewPreparacaoMapaBottom?._vm.AtualizarProgresso(0, $"Mapa carregado: {System.IO.Path.GetFileName(caminhoArquivo)}");
}
catch (Exception ex)
{
MapaCarregado = false;
_viewPreparacaoMapaBottom?._vm.AtualizarProgresso(0, $"Erro ao carregar mapa: {ex.Message}");
}
}
private async void OnFixarBaseSolicitado(MetodoFixacaoBase metodoFix, double? lat, double? lon, double? alt)
{
try
{
if (!(Models.Variaveis.GpsService.BaseFix?.FixLiberado ?? false))
{
bool fixar = false;
if (Models.Variaveis.GpsService.BaseFix?.PosicaoBaseFixada ?? false)
{
var res = System.Windows.MessageBox.Show(
"Mudar posição da base?",
"Tem certeza que deseja fixar a posição da base novamente?",
MessageBoxButton.YesNo,
MessageBoxImage.Question);
if (res == MessageBoxResult.Yes)
fixar = true;
}
else
{
fixar = true;
}
if (fixar)
{
_viewPreparacaoMapaBottom?._vm?.IniciarFixacao();
await Models.Variaveis.GpsService.ConfigurarModulo(true, metodoFix, lat, lon, alt);
}
}
else
{
Models.Variaveis.GpsService.BaseFix.ReiniciarFix();
BaseFixada = false;
}
}
catch (Exception ex)
{
_viewPreparacaoMapaBottom?._vm.FinalizarFixacao(false, $"Erro na fixação da base: {ex.Message}");
}
}
public void AtualizarProgressoFixacaoBase(double progresso, string status)
{
System.Windows.Application.Current.Dispatcher.BeginInvoke(new Action(() =>
{
_viewPreparacaoMapaBottom?._vm.AtualizarProgresso(progresso, status);
}));
}
public void FinalizarFixacaoBase(bool sucesso, string mensagem)
{
System.Windows.Application.Current.Dispatcher.BeginInvoke(new Action(() =>
{
BaseFixada = sucesso;
_viewPreparacaoMapaBottom?._vm.FinalizarFixacao(sucesso, mensagem);
}));
}
public void CancelarFixacaoBase(string mensagem)
{
System.Windows.Application.Current.Dispatcher.BeginInvoke(new Action(() =>
{
BaseFixada = false;
_viewPreparacaoMapaBottom?._vm.CancelarFixacao(mensagem);
}));
}
private async void OnAplicarOffsetSolicitado(double? offsetFrontalCm, double? offsetLateralCm)
{
if (offsetFrontalCm == null || offsetLateralCm == null) return;
_viewPreparacaoMapaBottom?._vm.IniciarFixacao();
var gps = Models.Variaveis.GpsService;
gps.LeverArm = new GeoLeverArm(offsetCampoFrontalCm: offsetFrontalCm.Value, offsetCampoLateralCm: offsetLateralCm.Value);
(double lat, double lon) = gps.LeverArm.FixLeverArmLatLon_Fast(gps.BaseFix.LatitudeFix, gps.BaseFix.LongitudeFix, gps.BaseFix.OrientacaoFix, 5);
await Models.Variaveis.GpsService.ConfigurarModulo(true, MetodoFixacaoBase.Manual, lat, lon, gps.BaseFix.AltitudeElpsoidalFix, offset: true);
}
#endregion
#region TELA 3
public void AtualizarListaRovers(List<OperacaoParametrosModel> rovers_atual)
{
var cards = rovers_atual.Select(x => new RoverCardModel()
{
EquipamentoId = x.IP,
NumeroSerie = x.RoverId,
Status = x.DadosLeitura?.StatusRover ?? AgroBase.Models.Enums.StatusModulo.Desconectado
}).ToArray();
_viewOperacaoRight?._vm?.AtualizarListaRovers(cards);
foreach (var rover in cards)
{
if (!_viewOperacaoCenter?.Mapa?.markers?.Added(rover.NumeroSerie) ?? false)
{
var roverDados = VariaveisControleOperacao.RoversNaRede.FirstOrDefault(x => x.RoverId == rover.NumeroSerie);
if (roverDados != null)
{
_viewOperacaoCenter?.Mapa?.markers?.AddMarker(
rover.NumeroSerie,
false,
lat: roverDados.DadosLeitura?.Gnss?.Latitude ?? 0,
lon: roverDados.DadosLeitura?.Gnss?.Longitude ?? 0,
heading: roverDados.DadosLeitura?.Gnss?.OrientacaoReal ?? 0,
rawGnssLat: roverDados.DadosLeitura?.Gnss?.LatitudeAnt ?? 0,
rawGnssLon: roverDados.DadosLeitura?.Gnss?.LongitudeAnt ?? 0
);
}
}
}
}
public void AtualizarDadosTela(OperacaoParametrosModel rover)
{
if (rover == null) return;
var obj = rover.DadosLeitura;
if (obj == null) return;
// MAPA
var simulacao = obj.Controle?.SimulacaoMPC?.Select(x => new double[] { x.longitude, x.latitude })?.ToList();
_viewOperacaoCenter?.Mapa?.markers.UpdateMarkerPosition(rover.RoverId, lat: obj.Gnss?.Latitude, lon: obj.Gnss?.Longitude, heading: obj.Gnss?.OrientacaoReal, predict: simulacao, rawGnssLat: obj.Gnss?.LatitudeAnt, rawGnssLon: obj.Gnss?.LongitudeAnt);
if (_viewOperacaoCenter?.Mapa?.chbAcompanhar.IsChecked ?? false) _viewOperacaoCenter?.Mapa?.SetView(obj.Gnss?.Latitude, obj.Gnss?.Longitude);
_viewOperacaoCenter?.Mapa?.markers.UpdateMarkerInfo(rover.RoverId, status: obj.Operacao?.Status ?? AgroBase.Models.Enums.StatusOperacao.NaoIniciado);
// ALERTAS
_viewOperacaoBottom?._vm?.AtualizarListaAlertasTodosRovers();
if (rover.RoverId != VariaveisControleOperacao.SelectedRoverId) return;
AtualizarBarraSuperior(rover);
// ESQUERDA
var conexao = obj.ModulosSaude?.FirstOrDefault(x => x.modulo == T_Code.Ipb);
double saude_rede = conexao?.saude ?? 0;
double conexao_latencia = conexao?.detalhes?["avg_rtt"]?.Value<double?>() ?? 0.0;
double conexao_perda = conexao?.detalhes?["loss_pct"]?.Value<double?>() ?? 0.0;
double bwTot = conexao?.detalhes?["bw_total_mbps"]?.Value<double?>() ?? 0.0;
string comunicacao = $"{conexao_latencia:0.00} ms {bwTot:0.00} Mbps";
string comunicacao_extended = $"{conexao_latencia:0.00} ms {conexao_perda:F2}% {bwTot:0.00} Mbps";
_viewOperacaoLeft?._vm?.AtualizarRover(
rover?.Descricao ?? "",
obj.Controle,
obj.Refrigeracao?.Temperatura ?? 0,
obj.Bateria?.PercentualBateria ?? 0,
obj.Atuador?.PercentualReservatorio ?? 0,
$"{saude_rede}%",
$"{obj.Gnss?.QualidadeFix ?? TiposCorrecaoGPS.SemCorrecao} {obj.Gnss?.PrecisaoCm:F2} cm",
AgroBase.Models.GPSUtils.DistanciaEntrePontos(new AgroBase.Models.GPSModel() { Latitude = obj.Gnss?.Latitude ?? 0, Longitude = obj.Gnss?.Longitude ?? 0 }, Models.Variaveis.GpsService.UltimaLeitura),
obj.Operacao?.Iniciada ?? false
);
// DIREITA (RESUMO)
_viewOperacaoRight?.areaResumo?._vm?.AtualizarResumo(r =>
{
r.Operacao = (obj.Operacao?.Liberada ?? false) ? "🔓 Liberada" : "🔒 Bloqueada";
r.Modo = obj.Operacao == null ? "-" : obj.Operacao.Modo.ToString();
r.Status = obj.Operacao == null ? "-" : $"{obj.Operacao.Status}" + (obj.Operacao.Status == AgroBase.Models.Enums.StatusOperacao.Aguardando ? $" ({obj.Operacao.TempoAguardandoSegs:0}s)" : "");
r.Carro = obj.Trajetoria == null ? "-" : obj.Trajetoria.StatusCarro.ToString();
r.Temperatura = $"{(obj.Refrigeracao?.Temperatura ?? 0):F2} °C";
r.RuaAtual = obj.Trajetoria == null ? "-" : $"{obj.Trajetoria.CorredorAtualDistanciaPercorrida:F2} m / " + $"{obj.Trajetoria.CorredorAtualDistanciaTotal:0.00} m " + $"({obj.Trajetoria.CorredorAtualIdx + 1})";
r.AreaTotal = obj.Trajetoria == null ? "-" : $"{obj.Trajetoria.DistanciaPercorrida:0.00} m / " + $"{obj.Trajetoria.DistanciaTotal:0.00} m";
r.Bateria = obj.Bateria == null ? "-" : $"{obj.Bateria.TensaoInstantanea:0.00} V " + $"({TimeSpan.FromMinutes(obj.Bateria.TempoEstimadoRestanteMinutos):dd\\.hh\\:mm\\:ss} " + $"{obj.Bateria.DistanciaEstimadaRestanteMetros:0.00} m)";
r.Herbicida = obj.Atuador == null ? "-" : $"{obj.Atuador.VolumeReservatorioL:0.00} L " + $"({TimeSpan.FromMinutes(obj.Atuador.TempoEstimadoRestanteMinutos):hh\\:mm\\:ss} " + $"{obj.Atuador.DistanciaEstimadaRestanteMetros:0.00} m)";
r.Infestacao = obj.Atuador == null ? "-" : $"{obj.Atuador.HerbicidaPorAtuacaoMl:0.00} mL/atuação";
r.Conexao = comunicacao == null ? "-" : $"{comunicacao}";
r.Duracao = obj.Operacao == null ? "00:00:00 / 00:00:00" : $"{TimeSpan.FromSeconds(obj.Operacao.TempoDecorridoSegs):hh\\:mm\\:ss} / " + $"{(string.IsNullOrWhiteSpace(obj.Trajetoria?.TempoEstimadoOperacao) ? "00:00:00" : obj.Trajetoria.TempoEstimadoOperacao)}";
// Opcionais para progress bars, caso queira evoluir o resumo
r.RuaAtualPercentual = obj.Trajetoria?.PercentualRuaAtual ?? 0;
r.AreaTotalPercentual = obj.Trajetoria?.PercentualOperacao ?? 0;
r.BateriaPercentual = obj.Bateria?.PercentualBateria ?? 0;
r.HerbicidaPercentual = obj.Atuador?.PercentualReservatorio ?? 0;
r.InfestacaoPercentual = obj.Atuador?.PercentualErvasTerreno ?? 0;
});
// DIAGNOSTICO
AtualizarDadosDiagnostico(rover);
// CAMERAS
var snr = obj?.Cameras?.FirstOrDefault(x => x.dispositivo == AgroBase.Models.Enums.T_Code.Snr);
var cam = obj?.Cameras?.FirstOrDefault(x => x.dispositivo == AgroBase.Models.Enums.T_Code.Cam);
_viewOperacaoCenter?.Monitoramento?._vm?.AtualizarDadosCameras(snr, cam, obj?.OperadorVisual?.StatusCarro, obj?.Atuador?.PercentualErvasNoRadar);
// PULVERIZADOR
bool telaPulverizador = _viewOperacaoCenter?._vm?.ConteudoAtual == OperacaoCenterConteudo.Pulverizador;
var bomba = obj.Atuador?.Bombas?.FirstOrDefault(x => x.ID == "BMBLN");
var agitador = obj.Atuador?.Bombas?.FirstOrDefault(x => x.ID == "BMBAGT");
if (telaPulverizador)
{
_viewOperacaoCenter?.Pulverizador?._vm?.AtualizarParametrosTela(new Views.Operacao.Monitoramento.PulverizadorSnapshot()
{
StatusGeralPulverizador = (obj?.ModulosSaude?.FirstOrDefault(x => x.modulo == T_Code.Atu)?.status ?? StatusModulo.Desconectado).ToString(),
CameraErvasStatus = _viewOperacaoCenter?.Monitoramento?._vm?.CameraErvasStatus ?? "",
ModoPulverizacaoTexto = (rover?.Controle?.PulverizadorAutomatico ?? false) ? "Automático" : "Manual",
PulverizacaoLiberadaTexto = (obj?.ModulosSaude?.FirstOrDefault(x => x.modulo == T_Code.Atu)?.motivos?.Any() ?? false) ? "Liberado" : "Bloqueado",
StatusBombaTexto = (bomba?.ComandoEstado ?? false) ? "Ligado": "Desligado",
StatusBombaTextoLido = (bomba?.LeituraEstado ?? false) ? "Ligado": "Desligado",
PotenciaBombaValor = $"{(bomba?.ComandoPotencia ?? 0):F2} %",
PotenciaBombaValorLido = $"{(bomba?.ComandoPotencia ?? 0):F2} %",
ModoAgitadorTexto = (rover?.Controle?.AtuAgitadorModo ?? ModoAgitadorCalda.SemAgitacao).ToString(),
PotenciaAgitadorValor = $"{agitador?.ComandoPotencia ?? 0} %",
PotenciaAgitadorValorLido = $"{agitador?.LeituraPotencia ?? 0} %",
NivelTanqueValor = $"{(obj?.Atuador?.PercentualReservatorio ?? 0):F2} %",
NivelTanqueLitrosValor = $"{(obj?.Atuador?.VolumeReservatorioL ?? 0):F2} L",
PressaoLinhaValor = $"{(rover?.Controle?.AtuPressaoLinha ?? 0):F2} psi",
PressaoLinhaPsiValor = $"{(obj?.Atuador?.PressaoLinhaPsi ?? 0):F2} psi",
VazaoInstantaneaValor = $"{(obj?.Atuador?.VazaoInstantaneaMLs ?? 0):F2} mL/s",
VazaoMediaValor = $"média {(obj?.Atuador?.VazaoMediaMLs ?? 0):F2} mL/s",
AutonomiaDistanciaValor = $"{(obj?.Atuador?.DistanciaEstimadaRestanteMetros ?? 0):F2} m",
AutonomiaTempoValor = $"{FuncoesGlobais.ConverterSegundosParaHHmmss((int)(obj?.Atuador?.TempoEstimadoRestanteMinutos ?? 0) * 60)}",
VolumeVazadoValor = $"{(obj?.Atuador?.VolumeVazaoMl ?? 0):F2} mL",
TempoLigadoPulverizacaoValor = $"{FuncoesGlobais.ConverterSegundosParaHHmmss((int)(bomba?.TempoAtuado ?? 0) / 1000)}",
BicosAtivosValor = $"{(obj?.Atuador?.Bicos?.Count(x => x.ComandoEstado == true) ?? 0)} / {obj?.Atuador?.Bicos?.Count ?? 0}",
InfoComplementarBicosValor = $"vazão média: {(obj?.Atuador?.Bicos?.Where(x => x.ComandoEstado == true)?.Average(x => x.VazaoInstantaneaMLs) ?? 0)} mL/s",
PercentualErvasRadar = $"radar: {(obj?.Atuador?.PercentualErvasNoRadar ?? 0)} %",
PercentualErvasTerreno = $"terreno: {(obj?.Atuador?.PercentualErvasTerreno ?? 0)} %",
});
}
var ATU = telaPulverizador ? _viewOperacaoCenter.Pulverizador.areaPulverizador : _viewOperacaoCenter.Monitoramento.Pulverizador;
ATU.ComprimentoBarraCm = AgroBase.Models.VariaveisEquipamento.ComprimentoBarraPulverizadoraCm;
ATU.DistanciaEntreBicosCm = AgroBase.Models.VariaveisEquipamento.DistanciaEntreBicosCm;
//ATU.AlturaBarra = obj?.Controle?.AlturaBarra ?? AgroBase.Models.VariaveisEquipamento.AlturaBarraPulverizadoraCm;
ATU.IsBombaOn = bomba?.LeituraEstado ?? false;
ATU.PressaoLinha = obj?.Atuador?.PressaoLinhaPsi ?? 0;
ATU.VazaoInstantanea = obj?.Atuador?.VazaoInstantaneaMLs ?? 0;
ATU.TempoAtuado = (bomba?.TempoAtuado ?? 0) / 1000.0;
double erroLateral = ((obj?.Trajetoria?.DistanciaEsquerda ?? 0) - (obj?.Trajetoria?.DistanciaDireita ?? 0)) / 2.0 * 100.0;
ATU.LarguraRuaCm = 100.0;
ATU.ErroLateralCm = erroLateral;
if (ATU.QtdBicos != obj?.Atuador?.Bicos?.Count)
{
ATU.QtdBicos = obj?.Atuador?.Bicos?.Count ?? AgroBase.Models.VariaveisEquipamento.QuantidadeBicosPulverizadores;
}
foreach (var bico in ATU.Bicos)
{
var _bc = obj?.Atuador?.Bicos?.FirstOrDefault(x => (x.Posicao - 1) == bico.Index);
if (_bc == null) continue;
bico.OpeningAngle = _bc.AnguloAbertura;
bico.AnguloControle = _bc.ComandoAngulo;
bico.IsCommandOn = _bc.ComandoEstado;
bico.IsSpraying = _bc.LeituraEstado;
bico.Vazao = _bc.VazaoInstantaneaMLs;
bico.Atuacoes = _bc.QtdAtuacoes;
bico.TempoAtuado = _bc.TempoAtuado / 1000.0;
}
// HEADING
var HDG = _viewOperacaoCenter.Monitoramento.Heading;
HDG.Heading = obj?.Gnss?.OrientacaoReal ?? double.NaN;
HDG.CourseHeading = obj?.Trajetoria?.AnguloCaminho ?? double.NaN;
// ATTITUDE
var IMU = _viewOperacaoCenter.Monitoramento.Attitude;
if (obj?.Imu?.InclinacaoLateral != null) IMU.PitchDeg = (double)obj.Imu.InclinacaoLateral;
if (obj?.Imu?.InclinacaoFrontal != null) IMU.RollDeg = (double)obj.Imu.InclinacaoFrontal;
IMU.LateralError = erroLateral;
}
private void AbrirDiagnosticoPeloAlerta(AlertaModel alerta)
{
if (alerta == null)
return;
_viewOperacaoRight?._vm?.SelecionarRover(alerta.Rover_ID);
_viewOperacaoRight?._vm?.SelecionarSecao(SecaoRightBar.Diagnostico);
_viewOperacaoCenter?.Diagnostico?._vm?.AbrirModuloPorAlerta(alerta.Modulo, alerta.Mod_ID);
}
public void AtualizarDadosDiagnostico(OperacaoParametrosModel? rover)
{
_viewOperacaoCenter?.Diagnostico?._vm?.AtualizarDados(rover);
_viewOperacaoCenter?.Diagnostico?.AtualizarGraficos();
}
public void AdicionarAlerta(string roverId, AgroBase.Models.Enums.T_Code modulo, SeveridadeAlerta severidade, string mensagem, string modId = null)
{
_viewOperacaoBottom?._vm?.AdicionarAlerta(roverId, modulo, severidade, mensagem, modId);
}
public void RemoverAlerta(string roverId, AgroBase.Models.Enums.T_Code modulo, SeveridadeAlerta? severidade = null, string modId = null)
{
_viewOperacaoBottom?._vm?.RemoverAlerta(roverId, modulo, severidade, modId);
}
private void OnRoverSelecionadoChanged(string roverId)
{
_viewOperacaoRight?._vm?.DestacarRoverNoMapa(roverId);
}
private void OnRoverSelecionadoChanged(RoverCardModel rover)
{
bool dados_base = rover == null;
if (dados_base)
{
if (!VariaveisControleOperacao.BaseEmFoco)
{
_viewOperacaoCenter?.Monitoramento?.PararStreamCameraFrontal();
_viewOperacaoCenter?.Monitoramento?.PararStreamCameraErvas();
VariaveisControleOperacao.EnviarComandoIniciarUDP(VariaveisControleOperacao.RoverEmFoco?.IP, false);
}
AtualizarDadosMapa(VariaveisControleOperacao.RoverEmFoco);
VariaveisControleOperacao.SelectedRoverId = VariaveisControleOperacao.BaseMarkerID;
_viewOperacaoCenter?.Mapa?.markers?.SetMarkerFocused(VariaveisControleOperacao.SelectedRoverId, true);
_viewOperacaoCenter?._vm?.SelecionarRoverLista(rover);
AtualizarBarraSuperior(StatusModulo.Conectado, "BASE", "VISÃO GERAL", "Selecione um equipamento na lista à direita para configurá-lo", "NORMAL", "Aguardando");
_viewOperacaoLeft?._vm?.DefinirSemRover();
}
else
{
VariaveisControleOperacao.SelectedRoverId = (rover.NumeroSerie ?? "").ToString();
_viewOperacaoCenter?.Mapa?.markers?.SetMarkerFocused(VariaveisControleOperacao.SelectedRoverId, true);
AtualizarDadosTela(VariaveisControleOperacao.RoverEmFoco);
_viewOperacaoCenter?.Monitoramento?.IniciarStreamCameraFrontal();
_viewOperacaoCenter?.Monitoramento?.IniciarStreamCameraErvas();
VariaveisControleOperacao.EnviarComandoIniciarUDP(VariaveisControleOperacao.RoverEmFoco?.IP, true);
_viewOperacaoCenter?._vm?.SelecionarRoverLista(rover);
AtualizarDadosMapa(VariaveisControleOperacao.RoverEmFoco);
AtualizarBarraSuperior(VariaveisControleOperacao.RoverEmFoco);
VariaveisControleOperacao.RequisitarParametrosOperacao();
}
}
private void OnSecaoSelecionadaChanged(SecaoRightBar secao)
{
switch (secao)
{
case SecaoRightBar.Parametrizacao:
VariaveisControleOperacao.RequisitarParametrosOperacao();
break;
case SecaoRightBar.Pulverizador:
if (_viewOperacaoCenter.Monitoramento.videoWeed.imageName != _viewOperacaoCenter.Pulverizador.imgVideo.Name)
{
_viewOperacaoCenter.Monitoramento.videoWeed.Parar();
_viewOperacaoCenter.Monitoramento.videoWeed = new TcpVideoReceiver(5002, _viewOperacaoCenter.Pulverizador.imgVideo);
_viewOperacaoCenter.Monitoramento.videoWeed.Iniciar();
}
break;
default:
if (_viewOperacaoCenter.Monitoramento.videoWeed.imageName != _viewOperacaoCenter.Monitoramento.imgVideoWeed.Name)
{
_viewOperacaoCenter.Monitoramento.videoWeed.Parar();
_viewOperacaoCenter.Monitoramento.videoWeed = new TcpVideoReceiver(5002, _viewOperacaoCenter.Monitoramento.imgVideoWeed);
_viewOperacaoCenter.Monitoramento.videoWeed.Iniciar();
}
break;
}
_viewOperacaoCenter?._vm?.DefinirSecao(secao);
AtualizarDadosMapa(VariaveisControleOperacao.RoverEmFoco);
}
private void OnLerParametrosSolicitado()
{
if (VariaveisControleOperacao.RoverEmFoco == null)
return;
VariaveisControleOperacao.RequisitarParametrosOperacao();
}
private void OnSalvarParametrosSolicitado(OperacaoParametrosModel parametros)
{
var rover = VariaveisControleOperacao.RoverEmFoco;
if (parametros.Modo == AgroBase.Models.Enums.ModoOperacao.RetornoBase && !(rover.DadosLeitura?.Operacao?.Iniciada ?? false))
{
var pontos = _viewOperacaoCenter?.Mapa?._pontosSelecionados;
if (!(pontos?.Any() ?? false))
{
System.Windows.MessageBox.Show("Clique no mapa para marcar os pontos por onde o equipamento deve seguir", "Pontos não marcados", MessageBoxButton.OK, MessageBoxImage.Warning);
return;
}
if (System.Windows.MessageBox.Show($"Deseja iniciar a operação de retorno seguindo os {pontos.Count} pontos marcados no mapa, somando em {GPSUtils.DistanciaDoTrecho(pontos):F2} metros?", "Confirmação", MessageBoxButton.YesNo, MessageBoxImage.Question) == MessageBoxResult.Yes)
{
parametros.PontosRetorno = pontos.Select(x => new double[] { x.Latitude, x.Longitude }).ToList();
VariaveisControleOperacao.EnviarComandoRetornoBase(pontosRetorno: parametros.PontosRetorno);
rover.PontosRetorno = parametros.PontosRetorno;
Task.Run(async () =>
{
await Task.Delay(500);
_viewOperacaoRight?._vm?.SelecionarSecao(SecaoRightBar.Resumo);
});
}
return;
}
var tipoMapa = _viewOperacaoCenter?.Mapa?.TipoMapaSelecionado ?? TipoMapaOperacao.Indefinido;
var dadosMapa = _viewOperacaoCenter?.Mapa?.CriarDadosMapa();
var ruasPercorrer = _viewOperacaoCenter?.Mapa?.RuasMapaCarregado?.Where(x => x.Selected)?.OrderBy(x => x.OrderSelection.Value)?.Select(x => x.Id)?.ToList() ?? new List<string>();
if (rover?.DadosLeitura?.Operacao?.Modo != parametros.Modo && (rover?.DadosLeitura?.Operacao?.Iniciada ?? false))
{
System.Windows.MessageBox.Show($"Já existe uma operação {rover?.DadosLeitura?.Operacao?.Modo ?? AgroBase.Models.Enums.ModoOperacao.NaoDefinido} em andamento. Finalize a operação atual para salvar os novos parametros.", "Mudança de Operação", MessageBoxButton.OK, MessageBoxImage.Warning);
return;
}
if (!(rover?.DadosLeitura?.Operacao?.Iniciada ?? false) && parametros.Modo == AgroBase.Models.Enums.ModoOperacao.MapaGPS && ((dadosMapa?.features?.Count ?? 0) == 0 || !ruasPercorrer.Any()))
{
System.Windows.MessageBox.Show("Selecione as ruas no mapa onde o equipamento irá operar", "Ruas não selecionadas", MessageBoxButton.OK, MessageBoxImage.Warning);
return;
}
if (rover == null)
return;
if (parametros?.Controle?.MovimentoAutomatico ?? false)
{
var _mov = parametros?.ModulosMandatorios?.FirstOrDefault(x => x.Dispositivo == T_Code.Mov);
if (_mov == null)
{
_mov = new AgroBase.Models.OperacaoModulosMandatoriosModel()
{
Dispositivo = T_Code.Mov,
Utilizar = true,
Mandatorio = true,
ComponentesEmUso = new Dictionary<string, (bool, bool)>()
{
{ "ET", (true, true) },
{ "DT", (true, true) },
{ "EF", (true, true) },
{ "DF", (true, true) },
}
};
}
else
{
foreach (var key in _mov.ComponentesEmUso?.Keys.ToList() ?? new List<string>())
{
_mov.ComponentesEmUso[key] = (true, true);
}
_mov.Utilizar = true;
_mov.Mandatorio = true;
}
}
if (parametros?.Controle?.DirecionalAutomatico ?? false)
{
var _dir = parametros?.ModulosMandatorios?.FirstOrDefault(x => x.Dispositivo == T_Code.Dir);
if (_dir == null)
{
_dir = new AgroBase.Models.OperacaoModulosMandatoriosModel()
{
Dispositivo = T_Code.Dir,
Utilizar = true,
Mandatorio = true,
ComponentesEmUso = new Dictionary<string, (bool, bool)>()
{
{ "ET", (true, true) },
{ "DT", (true, true) },
{ "EF", (true, true) },
{ "DF", (true, true) },
}
};
}
else
{
foreach (var key in _dir.ComponentesEmUso?.Keys.ToList() ?? new List<string>())
{
_dir.ComponentesEmUso[key] = (true, true);
}
_dir.Utilizar = true;
_dir.Mandatorio = true;
}
}
if (parametros?.Controle?.PulverizadorAutomatico ?? false)
{
var _atu = parametros?.ModulosMandatorios?.FirstOrDefault(x => x.Dispositivo == T_Code.Atu);
if (_atu == null)
{
_atu = new AgroBase.Models.OperacaoModulosMandatoriosModel()
{
Dispositivo = T_Code.Atu,
Utilizar = true,
Mandatorio = true,
ComponentesEmUso = new Dictionary<string, (bool, bool)>()
{
{ "MASRS", (true, true) },
{ "FLXLN", (true, true) },
{ "PRSLN", (true, true) },
{ "BOMBA", (true, true) },
{ "B01", (true, true) },
{ "B02", (true, true) },
{ "B03", (true, true) },
{ "B04", (true, true) },
{ "B05", (true, true) },
{ "B06", (true, true) },
{ "B07", (true, true) },
}
};
}
else
{
foreach (var key in _atu.ComponentesEmUso?.Keys.ToList() ?? new List<string>())
{
_atu.ComponentesEmUso[key] = (true, true);
}
_atu.Utilizar = true;
_atu.Mandatorio = true;
}
}
if (parametros?.Controle?.ImuParadaPorInclinacao ?? false)
{
var _imu = parametros.ModulosMandatorios?.FirstOrDefault(x => x.Dispositivo == T_Code.Imu);
if (_imu == null)
{
_imu = new AgroBase.Models.OperacaoModulosMandatoriosModel()
{
Dispositivo = T_Code.Imu,
Utilizar = true,
Mandatorio = true,
};
parametros?.ModulosMandatorios?.Add(_imu);
}
else
{
_imu.Utilizar = true;
_imu.Mandatorio = true;
}
}
if (parametros?.Controle?.OakParadaPorObstaculo ?? false)
{
var _snr = parametros.ModulosMandatorios?.FirstOrDefault(x => x.Dispositivo == T_Code.Snr);
if (_snr == null)
{
_snr = new AgroBase.Models.OperacaoModulosMandatoriosModel()
{
Dispositivo = T_Code.Snr,
Utilizar = true,
Mandatorio = true,
};
parametros?.ModulosMandatorios?.Add(_snr);
}
else
{
_snr.Utilizar = true;
_snr.Mandatorio = true;
}
}
var novosParametros = new OperacaoParametrosModel()
{
Modo = parametros.Modo,
Descricao = parametros.Descricao,
QtdCamerasSolo = parametros.QtdCamerasSolo,
QtdBicos = parametros.QtdBicos,
CapacidadeReservatorio = parametros.CapacidadeReservatorio,
Controle = parametros.Controle,
ModulosMandatorios = parametros?.ModulosMandatorios,
ParametrosMandatorios = parametros?.ParametrosMandatorios,
TipoMapa = tipoMapa,
RuasPercorrer = ruasPercorrer,
Mapa = dadosMapa
};
VariaveisControleOperacao.EnviarParametrosOperacao(novosParametros);
rover.Modo = novosParametros.Modo;
rover.Descricao = novosParametros.Descricao;
rover.QtdCamerasSolo = novosParametros.QtdCamerasSolo;
rover.QtdBicos = novosParametros.QtdBicos;
rover.CapacidadeReservatorio = novosParametros.CapacidadeReservatorio;
rover.Controle = novosParametros.Controle;
rover.ModulosMandatorios = novosParametros.ModulosMandatorios;
rover.ParametrosMandatorios = novosParametros.ParametrosMandatorios;
rover.PontosRetorno = novosParametros.PontosRetorno;
rover.TipoMapa = novosParametros.TipoMapa;
rover.RuasPercorrer = novosParametros.RuasPercorrer;
rover.Mapa = novosParametros.Mapa;
AtualizarDadosDiagnostico(rover);
Task.Run(async () =>
{
await Task.Delay(500);
_viewOperacaoRight?._vm?.SelecionarSecao(SecaoRightBar.Diagnostico);
});
}
#endregion
}
public enum ModoOperacao
{
Automatico = 1,
Manual = 2
}
public enum DockStep
{
ConfigConexao = 1,
PreparacaoMapa = 2,
ParametrizacaoRover = 3
}
}