利用串口DSR/CTS等端口获取市电状态并实现断电自动关机的C#程序
我有一个UPS,自带的关机软件有点问题,后台有javaw.exe占满一个CPU核心。本来我也懒得弄,这个自带的软件是用网页上的flash作为设置界面,最近不是flash用不了了吗,然后我也懒得再找办法继续运行这个flash,而且它还有占用CPU这个问题,所以就有想法弄一个自动关机的玩意。原计划是用单片机检测的,但是想想看串口那几个没多大用的端口,正好可以用来检测电平,也不知道有没有人像我这么干的,反正能用就好。下面两个是Program.cs和Form1.cs的代码:
Program.cs
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 |
using System; using System.Collections.Generic; using System.Diagnostics; using System.Linq; using System.Threading.Tasks; using System.Windows.Forms; namespace serialguanji { static class Program { /// <summary> /// 应用程序的主入口点。 /// </summary> [STAThread] static void Main() { //获取当前进程的ID int pId = Process.GetCurrentProcess().Id; bool isRun = false; foreach (Process p in Process.GetProcessesByName(Process.GetCurrentProcess().ProcessName)) { //取得当前程序的进程,进行比较 if (System.Reflection.Assembly.GetExecutingAssembly().Location.ToLower() == p.MainModule.FileName.ToLower()) { if (pId != p.Id) { isRun = true; break; } } } if (isRun == true) { MessageBox.Show("已经有实例在运行"); Application.Exit(); return; } Application.EnableVisualStyles(); Application.SetCompatibleTextRenderingDefault(false); Application.Run(new Form1()); } } } |
Form1.cs
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 |
using System; using System.IO; using System.Text; using System.Threading; using System.Threading.Tasks; using System.Windows.Forms; using System.IO.Ports; using System.Management; using System.Diagnostics; namespace serialguanji { public partial class Form1 : Form { string spx; SerialPort sp; CancellationTokenSource cancelTokenSource; Task task1; public class ErrorLog { public static void ErrorLogTxt(Exception ex) { //获取文件路径(相对于程序的基目录路径) string FilePath = AppDomain.CurrentDomain.BaseDirectory + "/Error.log"; StringBuilder msg = new StringBuilder(); msg.Append("———————————————————— \r\n"); msg.AppendFormat(" 异常发生时间: {0} \r\n", DateTime.Now); msg.AppendFormat(" 异常类型: {0} \r\n", ex.HResult); msg.AppendFormat(" 导致当前异常的 Exception 实例: {0} \r\n", ex.InnerException); msg.AppendFormat(" 导致异常的应用程序或对象的名称: {0} \r\n", ex.Source); msg.AppendFormat(" 引发异常的方法: {0} \r\n", ex.TargetSite); msg.AppendFormat(" 异常堆栈信息: {0} \r\n", ex.StackTrace); msg.AppendFormat(" 异常消息: {0} ", ex.Message); try { using (StreamWriter tw = File.AppendText(FilePath)) { tw.WriteLine(msg.ToString()); } } catch (Exception exx) { MessageBox.Show(exx.Message); } } public static void LogInfo(string sss) { //获取文件路径(相对于程序的基目录路径) string FilePath = AppDomain.CurrentDomain.BaseDirectory + "/Info.log"; StringBuilder msg = new StringBuilder(); msg.AppendFormat("{0} - ", DateTime.Now); msg.Append(sss); try { using (StreamWriter tw = File.AppendText(FilePath)) { tw.WriteLine(msg.ToString()); } } catch (Exception exx) { MessageBox.Show(exx.Message); } } } public Form1() { InitializeComponent(); } private void Form1_Shown(object sender, EventArgs e) { var search = new ManagementObjectSearcher(@"SELECT * FROM Win32_PnPEntity WHERE Name LIKE '%(COM%'"); ErrorLog.LogInfo("程序已启动"); comboBox1.Items.Clear(); foreach (ManagementObject mo1 in search.Get()) { comboBox1.Items.Add(mo1["Name"].ToString() + Environment.NewLine); if ((mo1["Name"].ToString().Contains("CH340")) || (mo1["Name"].ToString().Contains("PL2303"))) { spx = mo1["Name"].ToString() + Environment.NewLine; } } if (spx == null) { ErrorLog.LogInfo("找不到串口CH340"); MessageBox.Show("找不到串口CH340!请确认是否已连接模块。"); } else comboBox1.SelectedIndex = comboBox1.Items.IndexOf(spx); } private void comboBox1_SelectedIndexChanged(object sender, EventArgs e) { if (task1 != null && (task1.Status == TaskStatus.Running || task1.Status == TaskStatus.WaitingToRun || task1.Status == TaskStatus.WaitingForActivation)) { cancelTokenSource.Cancel(); cancelTokenSource.Dispose(); } try { if (sp != null && sp.IsOpen == true) sp.Close(); sp = new SerialPort(comboBox1.Text.Substring(comboBox1.Text.IndexOf("(") + 1, comboBox1.Text.Length - comboBox1.Text.IndexOf("(") - 4)); sp.Open(); Application.DoEvents(); cancelTokenSource = new CancellationTokenSource(); task1 = Task.Factory.StartNew(DoWork, cancelTokenSource.Token); this.WindowState = FormWindowState.Minimized; this.ShowInTaskbar = false; this.Hide(); ErrorLog.LogInfo("程序已正常工作"); } catch (Exception ex) { MessageBox.Show(ex.Message); ErrorLog.ErrorLogTxt(ex); } } private void Form1_FormClosing(object sender, FormClosingEventArgs e) { if (task1 != null && (task1.Status == TaskStatus.Running || task1.Status == TaskStatus.WaitingToRun || task1.Status == TaskStatus.WaitingForActivation)) { cancelTokenSource.Cancel(); cancelTokenSource.Dispose(); } if (sp != null && sp.IsOpen == true) sp.Close(); ErrorLog.LogInfo("程序退出"); } private void DoWork(object arg) { int mmm = 0, nnn = 0; while (!cancelTokenSource.IsCancellationRequested) // Worker thread loop { //if (sp.CtsHolding == false) if (sp.DsrHolding == false) mmm++; else if (nnn == 1) { mmm = 0; nnn = 0; ErrorLog.LogInfo("取消关机"); Process.Start("c:/windows/system32/shutdown.exe", "-a"); Process.Start("c:/windows/system32/shutdown.exe", "-a -m 192.168.86.13"); } if (nnn == 0 && mmm > 10) { ErrorLog.LogInfo("关机"); Process.Start("c:/windows/system32/shutdown.exe", "-s -t 20"); Process.Start("c:/windows/system32/shutdown.exe", "-s -m 192.168.86.13 -t 20"); nnn = 1; } Thread.Sleep(1000); } } private void Form1_Deactivate(object sender, EventArgs e) { if (this.WindowState == FormWindowState.Minimized) { this.ShowInTaskbar = false; this.Hide(); } } private void notifyIcon1_DoubleClick(object sender, EventArgs e) { if (this.WindowState == FormWindowState.Minimized) { this.Show(); this.ShowInTaskbar = true; this.WindowState = FormWindowState.Normal; } } private void 显示界面ToolStripMenuItem_Click(object sender, EventArgs e) { this.Show(); this.ShowInTaskbar = true; this.WindowState = FormWindowState.Normal; } private void 隐藏界面ToolStripMenuItem_Click(object sender, EventArgs e) { this.WindowState = FormWindowState.Minimized; this.ShowInTaskbar = false; this.Hide(); } private void 退出ToolStripMenuItem_Click(object sender, EventArgs e) { this.Close(); } private void button1_Click(object sender, EventArgs e) { ErrorLog.LogInfo("手动取消关机"); Process.Start("c:/windows/system32/shutdown.exe", "-a"); Process.Start("c:/windows/system32/shutdown.exe", "-a -m 192.168.86.13"); } } } |