Vamos a programar #97 - Ver el rendimiento del PC usando arduino y C# (beta).
Hola de nuevo a todos, hace unos días mientras hacia algunas cosas en la computadora, apague el monitor mientras la PC hacia los suyo, pero al paso de una hora, comencé a prender el monitor cada diez minutos para poder ver si ya había terminado de trabajar, tras cinco encendidos, la computadora finalmente termino de hacer lo que estaba haciendo y proseguí con mi labor. Cómo se me hizo fastidioso apagar y prender el monitor en algo que se que va a tardar mucho, pero que sin embargo no tengo la certeza de cuanto va durar, decidí usar la vieja combinación de arduino y una pantalla LCD.
La mayor parte de aplicaciones que requieren tiempo para realizar su trabajo, consumen una gran cantidad de recursos, por lo que podemos conectar un arduino, y monitorear cual es la carga para el CPU, usualmente, si la actividad del CPU es mayor a 25%, podemos decir que aun se lleva a cabo un proceso. Para poder mostrar la información, usaremos de nueva cuenta un arduino y la pantalla LCD, tal y cómo lo hicimos con "Message Sender" (o la aplicación para ver cual era la ventana activa). En este caso, un programa en C# obtenía la información y la enviaba a arduino para poder desplegarla, cosa que también haremos ahora.
La aplicación en C#
El código en C# que sirve para enviar la información del uso del CPU a arduino es el que sigue.
using System; using System.Windows.Forms; using System.IO.Ports; namespace CPUMeterToArduino { public partial class Form1 : Form { System.Diagnostics.PerformanceCounter CPULoad; System.Diagnostics.PerformanceCounter RAMInUse; System.Diagnostics.PerformanceCounter AvailableRAM; private SerialPort Port = new SerialPort(); private void ArduinoMessage(string Message) { try { Port.Write(Message); } catch (Exception e) { MessageBox.Show(e.Message, "Error", MessageBoxButtons.OK, MessageBoxIcon.Error); } } private void DataReceivedHandler(object sender, SerialDataReceivedEventArgs e) { string DATA = string.Concat("CPU ", CPULoad.NextValue().ToString("F2"), "%", " Ram ", PercentRAM(RAMInUse.NextValue(), AvailableRAM.NextValue()), "%"); SerialPort sp = (SerialPort)sender; string indata = sp.ReadExisting(); if (indata.Contains("\r\n")) { ArduinoMessage(DATA); } } Timer TimerMain; private int PercentRAM(float InUse, float Available) { if (Available == 0) return 100; else { float RamMBInUse = (InUse / 1024 / 1024); float TotalRam = RamMBInUse + Available; float Percent = ((RamMBInUse / TotalRam) * 100); return (int)Percent; } } public Form1() { InitializeComponent(); } private void Form1_Load(object sender, System.EventArgs e) { RAMInUse = new System.Diagnostics.PerformanceCounter("Memory", "Committed Bytes"); AvailableRAM = new System.Diagnostics.PerformanceCounter("Memory", "Available MBytes"); CPULoad = new System.Diagnostics.PerformanceCounter("Processor", "% Processor Time", "_Total"); TimerMain = new Timer(); TimerMain.Interval = 1000; TimerMain.Enabled = true; TimerMain.Tick += new System.EventHandler(TimerMain_Tick); string[] Ports = SerialPort.GetPortNames(); cboportname.Items.AddRange(Ports); cboportname.Text = "COM3"; Port.DataReceived += new SerialDataReceivedEventHandler(DataReceivedHandler); } private void TimerMain_Tick(object sender, EventArgs e) { PBCPUUsage.Value = (int)CPULoad.NextValue(); int PR = PercentRAM(RAMInUse.NextValue(), AvailableRAM.NextValue()); PBRAMUsage.Value = PR; this.Text = "Uso de RAM " + PR + "%"; NTFYMain.Text = "Uso de RAM " + PR + "%"; } private void Form1_Resize(object sender, EventArgs e) { if (this.WindowState == FormWindowState.Minimized) { Hide(); NTFYMain.Visible = true; } } private void NTFYMain_MouseDoubleClick(object sender, MouseEventArgs e) { Show(); this.WindowState = FormWindowState.Normal; NTFYMain.Visible = false; } private void Form1_FormClosing(object sender, FormClosingEventArgs e) { if (Port.IsOpen == true) { Port.Close(); } NTFYMain.Visible = false; } private void BtnConnect_Click(object sender, EventArgs e) { try { if (Port.IsOpen == false) { Port.BaudRate = 9600; Port.PortName = cboportname.Text; Port.Open(); } } catch (Exception ex) { MessageBox.Show(ex.Message, "Error", MessageBoxButtons.OK, MessageBoxIcon.Error); } } private void BtnDis_Click(object sender, EventArgs e) { if (Port.IsOpen == true) { Port.Write("Se ha desconectado el cliente"); Port.Close(); } } private void TSMIRestore_Click(object sender, EventArgs e) { NTFYMain_MouseDoubleClick(null, null); } private void TSMIExit_Click(object sender, EventArgs e) { Application.Exit(); } } }
Para poder utilizarlo requerimos de los siguientes controles:
- 2 ProgressBar
- PBCPUUsage
- PBRAMUsage
- 1 ComboBox
- cboportname
- 2 Button
- BtnConnect
- BtnDis
- 1 NotifyIcon
- NTFYMain
- 1 ContextMenuStrip
- CMSTray
El código en arduino.
#include <Wire.h> #include <LiquidCrystal_I2C.h> //SCL - A5 //SDA - A4 LiquidCrystal_I2C lcd(0x27,20,4); // set the LCD address to 0x27 for a 16 chars and 2 line display char Texto[80]; void setup() { lcd.init(); lcd.backlight(); Serial.begin(9600); } void loop() { int i = 0; if (Serial.available()) { while (Serial.available() > 0) { Texto[i] = Serial.read(); i++; } Texto[i] = '\0'; } lcd.clear(); lcd.setCursor(0 , 0); lcd.print(Texto); Serial.println("\r\n"); delay(1000); }
No hay comentarios.