Adaptado UserControl del PLCSim Advanced
This commit is contained in:
parent
e23e07b2c2
commit
72692cdf8c
|
@ -15,4 +15,10 @@
|
||||||
<PackageReference Include="OpenCvSharp4.Windows" Version="4.9.0.20240103" />
|
<PackageReference Include="OpenCvSharp4.Windows" Version="4.9.0.20240103" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<Reference Include="Siemens.Simatic.Simulation.Runtime.Api.x64">
|
||||||
|
<HintPath>C:\Program Files (x86)\Common Files\Siemens\PLCSIMADV\API\6.0\Siemens.Simatic.Simulation.Runtime.Api.x64.dll</HintPath>
|
||||||
|
</Reference>
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
</Project>
|
</Project>
|
||||||
|
|
|
@ -14,6 +14,7 @@ using System.Windows.Media.Imaging;
|
||||||
using static System.Runtime.InteropServices.JavaScript.JSType;
|
using static System.Runtime.InteropServices.JavaScript.JSType;
|
||||||
using System.Windows.Threading;
|
using System.Windows.Threading;
|
||||||
using CtrEditor.ObjetosSim;
|
using CtrEditor.ObjetosSim;
|
||||||
|
using CtrEditor.Siemens;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
// using System.Windows.Forms;
|
// using System.Windows.Forms;
|
||||||
using System.Text.Json.Serialization;
|
using System.Text.Json.Serialization;
|
||||||
|
@ -32,6 +33,7 @@ namespace CtrEditor
|
||||||
public ObservableCollection<string> listaImagenes { get; private set; } // Publicación de las claves del diccionario
|
public ObservableCollection<string> listaImagenes { get; private set; } // Publicación de las claves del diccionario
|
||||||
public ObservableCollection<TipoSimulable> ListaOsBase { get; } = new ObservableCollection<TipoSimulable>();
|
public ObservableCollection<TipoSimulable> ListaOsBase { get; } = new ObservableCollection<TipoSimulable>();
|
||||||
private ObservableCollection<osBase> _objetosSimulables = new ObservableCollection<osBase>();
|
private ObservableCollection<osBase> _objetosSimulables = new ObservableCollection<osBase>();
|
||||||
|
public PLCViewModel _plcViewModelData;
|
||||||
|
|
||||||
private SimulationManager simulationManager = new SimulationManager();
|
private SimulationManager simulationManager = new SimulationManager();
|
||||||
|
|
||||||
|
@ -52,6 +54,9 @@ namespace CtrEditor
|
||||||
OpenWorkDirectoryCommand = new RelayCommand(OpenWorkDirectory);
|
OpenWorkDirectoryCommand = new RelayCommand(OpenWorkDirectory);
|
||||||
datosDeTrabajo = new DatosDeTrabajo();
|
datosDeTrabajo = new DatosDeTrabajo();
|
||||||
|
|
||||||
|
// Inicializa el PLCViewModel
|
||||||
|
_plcViewModelData = new PLCViewModel();
|
||||||
|
|
||||||
InitializeTipoSimulableList();
|
InitializeTipoSimulableList();
|
||||||
|
|
||||||
ItemDoubleClickCommand = new ParameterizedRelayCommand(ExecuteDoubleClick);
|
ItemDoubleClickCommand = new ParameterizedRelayCommand(ExecuteDoubleClick);
|
||||||
|
@ -62,7 +67,6 @@ namespace CtrEditor
|
||||||
|
|
||||||
StartSimulationCommand = new RelayCommand(StartSimulation);
|
StartSimulationCommand = new RelayCommand(StartSimulation);
|
||||||
StopSimulationCommand = new RelayCommand(StopSimulation);
|
StopSimulationCommand = new RelayCommand(StopSimulation);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public void LoadInitialData()
|
public void LoadInitialData()
|
||||||
|
@ -161,6 +165,17 @@ namespace CtrEditor
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
public PLCViewModel PLCViewModel
|
||||||
|
{
|
||||||
|
get { return _plcViewModelData; }
|
||||||
|
set
|
||||||
|
{
|
||||||
|
_plcViewModelData = value;
|
||||||
|
OnPropertyChanged(nameof(PLCViewModel));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private string _selectedImage = null;
|
private string _selectedImage = null;
|
||||||
public string SelectedImage
|
public string SelectedImage
|
||||||
{
|
{
|
||||||
|
@ -241,7 +256,8 @@ namespace CtrEditor
|
||||||
var dataToSerialize = new SimulationData
|
var dataToSerialize = new SimulationData
|
||||||
{
|
{
|
||||||
ObjetosSimulables = ObjetosSimulables,
|
ObjetosSimulables = ObjetosSimulables,
|
||||||
UnitConverter = PixelToMeter.Instance.calc
|
UnitConverter = PixelToMeter.Instance.calc,
|
||||||
|
PLC_ConnectionData = PLCViewModel
|
||||||
};
|
};
|
||||||
|
|
||||||
var serializedData = JsonConvert.SerializeObject(dataToSerialize, settings);
|
var serializedData = JsonConvert.SerializeObject(dataToSerialize, settings);
|
||||||
|
@ -271,9 +287,14 @@ namespace CtrEditor
|
||||||
var simulationData = JsonConvert.DeserializeObject<SimulationData>(jsonString, settings);
|
var simulationData = JsonConvert.DeserializeObject<SimulationData>(jsonString, settings);
|
||||||
if (simulationData != null)
|
if (simulationData != null)
|
||||||
{
|
{
|
||||||
ObjetosSimulables = simulationData.ObjetosSimulables;
|
if (simulationData.ObjetosSimulables is not null)
|
||||||
|
ObjetosSimulables = simulationData.ObjetosSimulables;
|
||||||
|
|
||||||
|
if (simulationData.PLC_ConnectionData is not null)
|
||||||
|
PLCViewModel = simulationData.PLC_ConnectionData;
|
||||||
|
else
|
||||||
|
PLCViewModel = new PLCViewModel();
|
||||||
|
|
||||||
// Restaura el UnitConverter si es necesario en otra parte de tu código
|
|
||||||
PixelToMeter.Instance.calc = simulationData.UnitConverter;
|
PixelToMeter.Instance.calc = simulationData.UnitConverter;
|
||||||
|
|
||||||
// Recorrer la colección de objetos simulables
|
// Recorrer la colección de objetos simulables
|
||||||
|
@ -322,6 +343,7 @@ namespace CtrEditor
|
||||||
{
|
{
|
||||||
public ObservableCollection<osBase> ObjetosSimulables { get; set; }
|
public ObservableCollection<osBase> ObjetosSimulables { get; set; }
|
||||||
public UnitConverter UnitConverter { get; set; }
|
public UnitConverter UnitConverter { get; set; }
|
||||||
|
public PLCViewModel PLC_ConnectionData { get; set; }
|
||||||
}
|
}
|
||||||
|
|
||||||
public class TipoSimulable
|
public class TipoSimulable
|
||||||
|
|
|
@ -1,9 +1,10 @@
|
||||||
<Window x:Class="CtrEditor.MainWindow"
|
<Window
|
||||||
xmlns:ctreditor="clr-namespace:CtrEditor"
|
xmlns:ctreditor="clr-namespace:CtrEditor"
|
||||||
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
|
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
|
||||||
xmlns:i="http://schemas.microsoft.com/xaml/behaviors"
|
xmlns:i="http://schemas.microsoft.com/xaml/behaviors"
|
||||||
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
||||||
Height="450" Width="800"
|
xmlns:Siemens="clr-namespace:CtrEditor.Siemens" x:Class="CtrEditor.MainWindow"
|
||||||
|
Height="900" Width="1600"
|
||||||
ResizeMode="CanResize" Title="{Binding directorioTrabajo}">
|
ResizeMode="CanResize" Title="{Binding directorioTrabajo}">
|
||||||
|
|
||||||
<Window.DataContext>
|
<Window.DataContext>
|
||||||
|
@ -33,8 +34,9 @@
|
||||||
<!-- Primera Columna -->
|
<!-- Primera Columna -->
|
||||||
<Grid Grid.Column="0">
|
<Grid Grid.Column="0">
|
||||||
<Grid.RowDefinitions>
|
<Grid.RowDefinitions>
|
||||||
<RowDefinition Height="2*"/>
|
|
||||||
<RowDefinition Height="1*"/>
|
<RowDefinition Height="1*"/>
|
||||||
|
<RowDefinition Height="2*"/>
|
||||||
|
<RowDefinition Height="Auto"/>
|
||||||
</Grid.RowDefinitions>
|
</Grid.RowDefinitions>
|
||||||
<ListBox x:Name="ListaImagenes" Grid.Row="0" Margin="5" ItemsSource="{Binding listaImagenes}" SelectedItem="{Binding SelectedImage}" />
|
<ListBox x:Name="ListaImagenes" Grid.Row="0" Margin="5" ItemsSource="{Binding listaImagenes}" SelectedItem="{Binding SelectedImage}" />
|
||||||
<ListBox x:Name="ListaFunciones" Grid.Row="1" Margin="5" ItemsSource="{Binding ListaOsBase}" DisplayMemberPath="Nombre" SelectedItem="{Binding SelectedItem}">
|
<ListBox x:Name="ListaFunciones" Grid.Row="1" Margin="5" ItemsSource="{Binding ListaOsBase}" DisplayMemberPath="Nombre" SelectedItem="{Binding SelectedItem}">
|
||||||
|
@ -44,6 +46,7 @@
|
||||||
</i:EventTrigger>
|
</i:EventTrigger>
|
||||||
</i:Interaction.Triggers>
|
</i:Interaction.Triggers>
|
||||||
</ListBox>
|
</ListBox>
|
||||||
|
<Siemens:PLCControl x:Name="PLCSim" Grid.Row="2" Margin="5" DataContext="{Binding PLCViewModel}"/>
|
||||||
</Grid>
|
</Grid>
|
||||||
<!-- GridSplitter -->
|
<!-- GridSplitter -->
|
||||||
<GridSplitter Grid.Column="0" Grid.Row="0" HorizontalAlignment="Right" Width="5" Background="LightGray" />
|
<GridSplitter Grid.Column="0" Grid.Row="0" HorizontalAlignment="Right" Width="5" Background="LightGray" />
|
||||||
|
|
|
@ -10,6 +10,7 @@ using System.Windows.Media.Imaging;
|
||||||
using System.Windows.Navigation;
|
using System.Windows.Navigation;
|
||||||
using System.Windows.Shapes;
|
using System.Windows.Shapes;
|
||||||
using CtrEditor.ObjetosSim;
|
using CtrEditor.ObjetosSim;
|
||||||
|
using CtrEditor.Siemens;
|
||||||
using static System.Runtime.InteropServices.JavaScript.JSType;
|
using static System.Runtime.InteropServices.JavaScript.JSType;
|
||||||
using Binding = System.Windows.Data.Binding;
|
using Binding = System.Windows.Data.Binding;
|
||||||
using Label = System.Windows.Controls.Label;
|
using Label = System.Windows.Controls.Label;
|
||||||
|
|
|
@ -18,6 +18,8 @@ namespace CtrEditor.ObjetosSim
|
||||||
return new ucTransporteTTop();
|
return new ucTransporteTTop();
|
||||||
if (tipoObjeto == typeof(osGuia))
|
if (tipoObjeto == typeof(osGuia))
|
||||||
return new ucGuia();
|
return new ucGuia();
|
||||||
|
if (tipoObjeto == typeof(osTransporteGuias))
|
||||||
|
return new ucTransporteGuias();
|
||||||
|
|
||||||
// Puedes añadir más condiciones para otros tipos
|
// Puedes añadir más condiciones para otros tipos
|
||||||
|
|
||||||
|
@ -32,6 +34,8 @@ namespace CtrEditor.ObjetosSim
|
||||||
return new osTransporteTTop();
|
return new osTransporteTTop();
|
||||||
if (tipoObjeto == typeof(osGuia))
|
if (tipoObjeto == typeof(osGuia))
|
||||||
return new osGuia();
|
return new osGuia();
|
||||||
|
if (tipoObjeto == typeof(osTransporteGuias))
|
||||||
|
return new osTransporteGuias();
|
||||||
|
|
||||||
// Puedes añadir más condiciones para otros tipos
|
// Puedes añadir más condiciones para otros tipos
|
||||||
|
|
||||||
|
|
|
@ -11,7 +11,7 @@
|
||||||
</UserControl.Resources>
|
</UserControl.Resources>
|
||||||
|
|
||||||
<Canvas>
|
<Canvas>
|
||||||
<Rectangle Width="{Binding Ancho, Converter={StaticResource MeterToPixelConverter}}" Height="{Binding Alto, Converter={StaticResource MeterToPixelConverter}}" Fill="Blue">
|
<Rectangle Width="{Binding Ancho, Converter={StaticResource MeterToPixelConverter}}" Height="{Binding AltoGuia, Converter={StaticResource MeterToPixelConverter}}" Fill="Blue">
|
||||||
<Rectangle.RenderTransform>
|
<Rectangle.RenderTransform>
|
||||||
<RotateTransform Angle="{Binding Angulo}"/>
|
<RotateTransform Angle="{Binding Angulo}"/>
|
||||||
</Rectangle.RenderTransform>
|
</Rectangle.RenderTransform>
|
||||||
|
|
|
@ -54,13 +54,13 @@ namespace CtrEditor.ObjetosSim
|
||||||
OnPropertyChanged(nameof(Ancho));
|
OnPropertyChanged(nameof(Ancho));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
public float Alto
|
public float AltoGuia
|
||||||
{
|
{
|
||||||
get => Geometria.Width;
|
get => Geometria.Width;
|
||||||
set
|
set
|
||||||
{
|
{
|
||||||
Geometria.Width = value;
|
Geometria.Width = value;
|
||||||
OnPropertyChanged(nameof(Alto));
|
OnPropertyChanged(nameof(AltoGuia));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -90,7 +90,7 @@ namespace CtrEditor.ObjetosSim
|
||||||
public osGuia()
|
public osGuia()
|
||||||
{
|
{
|
||||||
Ancho = 1;
|
Ancho = 1;
|
||||||
Alto = 0.10f;
|
AltoGuia = 0.03f;
|
||||||
}
|
}
|
||||||
|
|
||||||
public override void ConnectSimManager(SimulationManager simulationManager)
|
public override void ConnectSimManager(SimulationManager simulationManager)
|
||||||
|
|
|
@ -5,9 +5,27 @@
|
||||||
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
|
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
|
||||||
xmlns:local="clr-namespace:CtrEditor.ObjetosSim"
|
xmlns:local="clr-namespace:CtrEditor.ObjetosSim"
|
||||||
mc:Ignorable="d"
|
mc:Ignorable="d"
|
||||||
d:DesignHeight="450" d:DesignWidth="800">
|
d:DesignHeight="300" d:DesignWidth="300">
|
||||||
|
|
||||||
|
<UserControl.Resources>
|
||||||
|
<local:MeterToPixelConverter x:Key="MeterToPixelConverter"/>
|
||||||
|
</UserControl.Resources>
|
||||||
|
|
||||||
<Grid>
|
<Grid>
|
||||||
|
<!-- Contenedor principal -->
|
||||||
|
<Grid.RowDefinitions>
|
||||||
|
<RowDefinition Height="Auto"/>
|
||||||
|
<RowDefinition Height="*"/>
|
||||||
|
<RowDefinition Height="Auto"/>
|
||||||
|
</Grid.RowDefinitions>
|
||||||
|
|
||||||
|
<!-- Borde superior -->
|
||||||
|
<Border Grid.Row="0" Height="5" Width="{Binding Ancho, Converter={StaticResource MeterToPixelConverter}}" Background="Blue"/>
|
||||||
|
|
||||||
|
<!-- Contenido central -->
|
||||||
|
<local:ucTransporteTTop Grid.Row="1"/>
|
||||||
|
|
||||||
|
<!-- Borde inferior -->
|
||||||
|
<Border Grid.Row="2" Height="5" Background="Blue"/>
|
||||||
</Grid>
|
</Grid>
|
||||||
</UserControl>
|
</UserControl>
|
||||||
|
|
|
@ -18,11 +18,142 @@ namespace CtrEditor.ObjetosSim
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Interaction logic for ucTransporteGuias.xaml
|
/// Interaction logic for ucTransporteGuias.xaml
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public partial class ucTransporteGuias : UserControl
|
public class osTransporteGuias : osBase
|
||||||
{
|
{
|
||||||
|
private string _nombre = "Transporte Guias";
|
||||||
|
|
||||||
|
private float frictionCoefficient;
|
||||||
|
private float velMax50hz; // en metros por minuto
|
||||||
|
private float tiempoRampa;
|
||||||
|
private bool esMarcha;
|
||||||
|
|
||||||
|
private Rectangle Geometria = new Rectangle();
|
||||||
|
|
||||||
|
public override float Left
|
||||||
|
{
|
||||||
|
get => Geometria.Left;
|
||||||
|
set
|
||||||
|
{
|
||||||
|
Geometria.Left = value;
|
||||||
|
CanvasSetLeftinMeter(value);
|
||||||
|
OnPropertyChanged(nameof(Left));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
public override float Top
|
||||||
|
{
|
||||||
|
get => Geometria.Top;
|
||||||
|
set
|
||||||
|
{
|
||||||
|
Geometria.Top = value;
|
||||||
|
CanvasSetTopinMeter(value);
|
||||||
|
OnPropertyChanged(nameof(Top));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public float Ancho
|
||||||
|
{
|
||||||
|
get => Geometria.Length;
|
||||||
|
set
|
||||||
|
{
|
||||||
|
Geometria.Length = value;
|
||||||
|
OnPropertyChanged(nameof(Ancho));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
public float Alto
|
||||||
|
{
|
||||||
|
get => Geometria.Width;
|
||||||
|
set
|
||||||
|
{
|
||||||
|
Geometria.Width = value;
|
||||||
|
OnPropertyChanged(nameof(Alto));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public float Angulo
|
||||||
|
{
|
||||||
|
get => Geometria.Angle;
|
||||||
|
set
|
||||||
|
{
|
||||||
|
Geometria.Angle = value;
|
||||||
|
OnPropertyChanged(nameof(Angulo));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
public float VelocidadActual
|
||||||
|
{
|
||||||
|
get => Geometria.Speed;
|
||||||
|
set
|
||||||
|
{
|
||||||
|
Geometria.Speed = value;
|
||||||
|
OnPropertyChanged(nameof(VelocidadActual));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public override string Nombre
|
||||||
|
{
|
||||||
|
get => _nombre;
|
||||||
|
set
|
||||||
|
{
|
||||||
|
if (_nombre != value)
|
||||||
|
{
|
||||||
|
_nombre = value;
|
||||||
|
OnPropertyChanged(nameof(Nombre));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public float FrictionCoefficient { get => frictionCoefficient; set => frictionCoefficient = value; }
|
||||||
|
public float VelMax50hz { get => velMax50hz; set => velMax50hz = value; }
|
||||||
|
public float TiempoRampa { get => tiempoRampa; set => tiempoRampa = value; }
|
||||||
|
public bool EsMarcha { get => esMarcha; set => esMarcha = value; }
|
||||||
|
|
||||||
|
public osTransporteGuias()
|
||||||
|
{
|
||||||
|
Ancho = 1;
|
||||||
|
Alto = 0.10f;
|
||||||
|
}
|
||||||
|
|
||||||
|
public override void ConnectSimManager(SimulationManager simulationManager)
|
||||||
|
{
|
||||||
|
simulationManager.rectangles.Add(Geometria);
|
||||||
|
}
|
||||||
|
public override void UpdateControl()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
public partial class ucTransporteGuias : UserControl, IDataContainer
|
||||||
|
{
|
||||||
|
public osBase? Datos { get; set; }
|
||||||
|
|
||||||
public ucTransporteGuias()
|
public ucTransporteGuias()
|
||||||
{
|
{
|
||||||
InitializeComponent();
|
InitializeComponent();
|
||||||
}
|
}
|
||||||
|
public void Resize(float width, float height)
|
||||||
|
{
|
||||||
|
if (Datos is osTransporteGuias datos)
|
||||||
|
datos.Ancho = PixelToMeter.Instance.calc.PixelsToMeters(width);
|
||||||
|
}
|
||||||
|
public void Move(float LeftPixels, float TopPixels)
|
||||||
|
{
|
||||||
|
if (Datos != null)
|
||||||
|
{
|
||||||
|
Datos.Left = PixelToMeter.Instance.calc.PixelsToMeters(LeftPixels);
|
||||||
|
Datos.Top = PixelToMeter.Instance.calc.PixelsToMeters(TopPixels);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
public void Rotate(float Angle)
|
||||||
|
{
|
||||||
|
if (Datos != null)
|
||||||
|
if (Datos is osTransporteGuias datos)
|
||||||
|
datos.Angulo = Angle;
|
||||||
|
}
|
||||||
|
public void Highlight(bool State) { }
|
||||||
|
public int ZIndex()
|
||||||
|
{
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,42 @@
|
||||||
|
<UserControl x:Class="CtrEditor.Siemens.PLCControl"
|
||||||
|
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
|
||||||
|
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
||||||
|
xmlns:local="clr-namespace:CtrEditor.Siemens">
|
||||||
|
|
||||||
|
<Grid>
|
||||||
|
<Grid.RowDefinitions>
|
||||||
|
<RowDefinition Height="*"/>
|
||||||
|
<RowDefinition Height="*"/>
|
||||||
|
<RowDefinition Height="*"/>
|
||||||
|
<RowDefinition Height="*"/>
|
||||||
|
<RowDefinition Height="*"/>
|
||||||
|
</Grid.RowDefinitions>
|
||||||
|
<Grid.ColumnDefinitions>
|
||||||
|
<ColumnDefinition Width="*"/>
|
||||||
|
<ColumnDefinition Width="2*"/>
|
||||||
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
|
<Label Content="IP:" Grid.Row="0" Grid.Column="0" Margin="1" VerticalAlignment="Center"/>
|
||||||
|
<TextBox Text="{Binding IP, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Grid.Row="0" Grid.Column="1" Margin="1" VerticalAlignment="Center"/>
|
||||||
|
|
||||||
|
<Label Content="Name:" Grid.Row="1" Grid.Column="0" Margin="1" VerticalAlignment="Center"/>
|
||||||
|
<TextBox Text="{Binding Name, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Grid.Row="1" Grid.Column="1" Margin="1" VerticalAlignment="Center"/>
|
||||||
|
|
||||||
|
<Button Content="Connect" Command="{Binding ConnectCommand}"
|
||||||
|
Grid.Row="2" Grid.Column="0" Margin="1" VerticalAlignment="Center"/>
|
||||||
|
<Button Content="Disconnect" Command="{Binding DisconnectCommand}"
|
||||||
|
Grid.Row="2" Grid.Column="1" Margin="1" VerticalAlignment="Center"/>
|
||||||
|
|
||||||
|
<Label Content="CPU cycle:" Grid.Row="3" Grid.Column="0" Margin="1" VerticalAlignment="Center"/>
|
||||||
|
<Label Content="{Binding CpuTime}" Grid.Row="3" Grid.Column="1" Margin="1" VerticalAlignment="Center"/>
|
||||||
|
<Label Grid.Row="4" Grid.Column="0" Margin="1" VerticalAlignment="Center">
|
||||||
|
Last Error:
|
||||||
|
</Label>
|
||||||
|
<Label Grid.Row="4" Grid.Column="1" Margin="1" VerticalAlignment="Center" HorizontalAlignment="Stretch">
|
||||||
|
<TextBlock Text="{Binding LastError}" TextWrapping="Wrap" Padding="3"/>
|
||||||
|
</Label>
|
||||||
|
|
||||||
|
</Grid>
|
||||||
|
</UserControl>
|
|
@ -0,0 +1,233 @@
|
||||||
|
using Siemens.Simatic.Simulation.Runtime;
|
||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.ComponentModel;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Runtime.CompilerServices;
|
||||||
|
using System.Text;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using System.Windows;
|
||||||
|
using System.Windows.Controls;
|
||||||
|
using System.Windows.Data;
|
||||||
|
using System.Windows.Documents;
|
||||||
|
using System.Windows.Input;
|
||||||
|
using System.Windows.Media;
|
||||||
|
using System.Windows.Media.Imaging;
|
||||||
|
using System.Windows.Navigation;
|
||||||
|
using System.Windows.Shapes;
|
||||||
|
using System.Windows.Threading;
|
||||||
|
|
||||||
|
namespace CtrEditor.Siemens
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Interaction logic for PLCControl.xaml
|
||||||
|
/// </summary>
|
||||||
|
public class PLCViewModel : INotifyPropertyChanged
|
||||||
|
{
|
||||||
|
private readonly PLCModel _plcModel;
|
||||||
|
private readonly DispatcherTimer _timer;
|
||||||
|
private string _cpuTime;
|
||||||
|
private string _connectionStatus = "offline";
|
||||||
|
private string _ip = "10.1.30.11";
|
||||||
|
private string _name = "PLC";
|
||||||
|
private string lastError;
|
||||||
|
|
||||||
|
public event PropertyChangedEventHandler PropertyChanged;
|
||||||
|
|
||||||
|
public PLCViewModel()
|
||||||
|
{
|
||||||
|
_plcModel = new PLCModel();
|
||||||
|
_timer = new DispatcherTimer { Interval = TimeSpan.FromMilliseconds(1000) };
|
||||||
|
_timer.Tick += (s, e) => Refresh();
|
||||||
|
|
||||||
|
ConnectCommand = new RelayCommand(Connect, () => true);
|
||||||
|
DisconnectCommand = new RelayCommand(Disconnect, () => true);
|
||||||
|
}
|
||||||
|
|
||||||
|
public string IP
|
||||||
|
{
|
||||||
|
get => _ip;
|
||||||
|
set
|
||||||
|
{
|
||||||
|
_ip = value;
|
||||||
|
OnPropertyChanged();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public string Name
|
||||||
|
{
|
||||||
|
get => _name;
|
||||||
|
set
|
||||||
|
{
|
||||||
|
_name = value;
|
||||||
|
OnPropertyChanged();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public string CpuTime
|
||||||
|
{
|
||||||
|
get => _cpuTime;
|
||||||
|
set
|
||||||
|
{
|
||||||
|
_cpuTime = value;
|
||||||
|
OnPropertyChanged();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public string ConnectionStatus
|
||||||
|
{
|
||||||
|
get => _connectionStatus;
|
||||||
|
set
|
||||||
|
{
|
||||||
|
_connectionStatus = value;
|
||||||
|
OnPropertyChanged();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public ICommand ConnectCommand { get; }
|
||||||
|
public ICommand DisconnectCommand { get; }
|
||||||
|
public string LastError
|
||||||
|
{
|
||||||
|
get => lastError;
|
||||||
|
set
|
||||||
|
{
|
||||||
|
lastError = value;
|
||||||
|
OnPropertyChanged();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void Connect()
|
||||||
|
{
|
||||||
|
// Implementa la conexión utilizando PLCModel
|
||||||
|
_plcModel.Instance = SimulationRuntimeManager.CreateInterface(Name);
|
||||||
|
_plcModel.Instance.OnSoftwareConfigurationChanged += Instance_OnSoftwareConfigurationChanged;
|
||||||
|
//_plcModel.Instance.CommunicationInterface = ECommunicationInterface.Softbus;
|
||||||
|
|
||||||
|
if (_plcModel.Instance != null)
|
||||||
|
{
|
||||||
|
_plcModel.UpdateTagList();
|
||||||
|
_timer.Start();
|
||||||
|
ConnectionStatus = "connected";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void Instance_OnSoftwareConfigurationChanged(IInstance instance, SOnSoftwareConfigChangedParameter event_param)
|
||||||
|
{
|
||||||
|
_plcModel.UpdateTagList();
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
private void Disconnect()
|
||||||
|
{
|
||||||
|
_timer.Stop();
|
||||||
|
ConnectionStatus = "offline";
|
||||||
|
_plcModel.Instance = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
private void Refresh()
|
||||||
|
{
|
||||||
|
if (_plcModel.Instance != null)
|
||||||
|
{
|
||||||
|
|
||||||
|
CpuTime = _plcModel.LeerInt16("\"DB HMI\".CPU_Scan_Time")?.ToString() ?? "N/A";
|
||||||
|
LastError = _plcModel.LastError;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void OnPropertyChanged([CallerMemberName] string propertyName = null)
|
||||||
|
{
|
||||||
|
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public class PLCModel
|
||||||
|
{
|
||||||
|
public IInstance Instance { get; set; }
|
||||||
|
public bool IsConfigured { get; set; }
|
||||||
|
public string LastError { get; set; }
|
||||||
|
|
||||||
|
public void UpdateTagList()
|
||||||
|
{
|
||||||
|
IsConfigured = false;
|
||||||
|
try
|
||||||
|
{
|
||||||
|
Instance?.UpdateTagList( ETagListDetails.IO | ETagListDetails.DB);
|
||||||
|
IsConfigured = true;
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
LastError = ex.Message;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public bool LeerSalidaBool(byte pByte, int pBit)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
return Instance?.OutputArea.ReadBit(pByte, (byte)pBit) ?? false;
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
LastError = ex.Message;
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void EscribirInputBool(byte pByte, int pBit, bool pValue)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
Instance?.InputArea.WriteBit(pByte, (byte)pBit, pValue);
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
LastError = ex.Message;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void EscribirTagBool(string pTag, bool pValue)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
Instance?.WriteBool(pTag, pValue);
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
LastError = pTag + ":" + ex.Message;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
public bool LeerTagBool(string pTag)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
return Instance?.ReadBool(pTag) ?? false;
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
LastError = pTag + ":" + ex.Message;
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public int? LeerInt16(string pTag)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
return Instance?.ReadInt16(pTag);
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
LastError = pTag + ":" + ex.Message;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public partial class PLCControl : UserControl
|
||||||
|
{
|
||||||
|
public PLCControl()
|
||||||
|
{
|
||||||
|
InitializeComponent();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,52 @@
|
||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Text;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using Siemens.Simatic;
|
||||||
|
using Siemens.Simatic.Simulation.Runtime;
|
||||||
|
|
||||||
|
namespace CtrEditor.Siemens
|
||||||
|
{
|
||||||
|
internal class PLCSim
|
||||||
|
{
|
||||||
|
SIPSuite4 plcIP;
|
||||||
|
|
||||||
|
}
|
||||||
|
public class PLCConnector
|
||||||
|
{
|
||||||
|
// Propiedades
|
||||||
|
public IInstance Instance { get; set; }
|
||||||
|
private bool IsConfigured { get; set; } = false;
|
||||||
|
private SIPSuite4 InstanceIP;
|
||||||
|
|
||||||
|
// Constructor
|
||||||
|
public PLCConnector(string instanceName, string pIP4)
|
||||||
|
{
|
||||||
|
InstanceIP = new SIPSuite4(pIP4, "255.255.255.0", "0.0.0.0");
|
||||||
|
Instance = SimulationRuntimeManager.CreateInterface(instanceName);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Métodos Públicos
|
||||||
|
public void PowerOnPLCInstance()
|
||||||
|
{
|
||||||
|
Instance.PowerOn(60000);
|
||||||
|
Instance.SetIPSuite(0, InstanceIP, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void PowerOffPLCInstance()
|
||||||
|
{
|
||||||
|
Instance.PowerOff(6000);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void RunPLCInstance()
|
||||||
|
{
|
||||||
|
Instance.Run(6000);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void StopPLCInstance()
|
||||||
|
{
|
||||||
|
Instance.Stop(6000);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in New Issue