Implemented APIC based CPU enumeration (Issue 41).
3 Version: MPL 1.1/GPL 2.0/LGPL 2.1
5 The contents of this file are subject to the Mozilla Public License Version
6 1.1 (the "License"); you may not use this file except in compliance with
7 the License. You may obtain a copy of the License at
9 http://www.mozilla.org/MPL/
11 Software distributed under the License is distributed on an "AS IS" basis,
12 WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
13 for the specific language governing rights and limitations under the License.
15 The Original Code is the Open Hardware Monitor code.
17 The Initial Developer of the Original Code is
18 Michael Möller <m.moeller@gmx.ch>.
19 Portions created by the Initial Developer are Copyright (C) 2009-2010
20 the Initial Developer. All Rights Reserved.
24 Alternatively, the contents of this file may be used under the terms of
25 either the GNU General Public License Version 2 or later (the "GPL"), or
26 the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
27 in which case the provisions of the GPL or the LGPL are applicable instead
28 of those above. If you wish to allow use of your version of this file only
29 under the terms of either the GPL or the LGPL, and not to allow others to
30 use your version of this file under the terms of the MPL, indicate your
31 decision by deleting the provisions above and replace them with the notice
32 and other provisions required by the GPL or the LGPL. If you do not delete
33 the provisions above, a recipient may use your version of this file under
34 the terms of any one of the MPL, the GPL or the LGPL.
39 using System.Collections.Generic;
40 using System.ComponentModel;
41 using System.Configuration;
45 using System.Windows.Forms;
46 using Aga.Controls.Tree;
47 using Aga.Controls.Tree.NodeControls;
48 using OpenHardwareMonitor.Hardware;
49 using OpenHardwareMonitor.Utilities;
51 namespace OpenHardwareMonitor.GUI {
52 public partial class MainForm : Form {
54 private Computer computer = new Computer();
56 private TreeModel treeModel;
57 private IDictionary<ISensor, Color> sensorPlotColors =
58 new Dictionary<ISensor, Color>();
59 private Color[] plotColorPalette;
60 private SensorSystemTray sensorSystemTray;
61 private NotifyIcon notifyIcon;
62 private StartupManager startupManager = new StartupManager();
65 InitializeComponent();
66 this.Font = SystemFonts.MessageBoxFont;
67 treeView.Font = SystemFonts.MessageBoxFont;
68 plotPanel.Font = SystemFonts.MessageBoxFont;
70 nodeCheckBox.IsVisibleValueNeeded +=
71 new EventHandler<NodeControlValueEventArgs>(
72 nodeCheckBox_IsVisibleValueNeeded);
73 nodeCheckBox.CheckStateChanged +=
74 new EventHandler<TreePathEventArgs>(UpdatePlotSelection);
75 nodeTextBoxText.DrawText +=
76 new EventHandler<DrawEventArgs>(nodeTextBoxText_DrawText);
77 nodeTextBoxValue.DrawText +=
78 new EventHandler<DrawEventArgs>(nodeTextBoxText_DrawText);
79 nodeTextBoxMin.DrawText +=
80 new EventHandler<DrawEventArgs>(nodeTextBoxText_DrawText);
81 nodeTextBoxMax.DrawText +=
82 new EventHandler<DrawEventArgs>(nodeTextBoxText_DrawText);
83 nodeTextBoxLimit.DrawText +=
84 new EventHandler<DrawEventArgs>(nodeTextBoxLimit_DrawText);
86 if (Utilities.Config.Contains("mainForm.Location.X")) {
87 int x = Utilities.Config.Get("mainForm.Location.X", Location.X);
89 int y = Utilities.Config.Get("mainForm.Location.Y", Location.Y);
91 this.Location = new Point(x, y);
93 StartPosition = FormStartPosition.CenterScreen;
96 Width = Utilities.Config.Get("mainForm.Width", Width);
97 Height = Utilities.Config.Get("mainForm.Height", Height);
99 treeModel = new TreeModel();
100 root = new Node(System.Environment.MachineName);
101 root.Image = Utilities.EmbeddedResources.GetImage("computer.png");
103 treeModel.Nodes.Add(root);
104 treeView.Model = treeModel;
106 notifyIcon = new NotifyIcon();
107 notifyIcon.ContextMenuStrip = this.notifyContextMenuStrip;
108 notifyIcon.Icon = EmbeddedResources.GetIcon("smallicon.ico");
109 notifyIcon.Text = "Open Hardware Monitor";
110 notifyIcon.DoubleClick += new EventHandler(this.hideShowClick);
112 sensorSystemTray = new SensorSystemTray(computer);
114 computer.HardwareAdded += new HardwareEventHandler(HardwareAdded);
115 computer.HardwareRemoved += new HardwareEventHandler(HardwareRemoved);
118 timer.Enabled = true;
120 plotColorPalette = new Color[14];
121 plotColorPalette[0] = Color.Blue;
122 plotColorPalette[1] = Color.OrangeRed;
123 plotColorPalette[2] = Color.Green;
124 plotColorPalette[3] = Color.LightSeaGreen;
125 plotColorPalette[4] = Color.Goldenrod;
126 plotColorPalette[5] = Color.DarkViolet;
127 plotColorPalette[6] = Color.YellowGreen;
128 plotColorPalette[7] = Color.SaddleBrown;
129 plotColorPalette[8] = Color.Gray;
130 plotColorPalette[9] = Color.RoyalBlue;
131 plotColorPalette[10] = Color.DeepPink;
132 plotColorPalette[11] = Color.MediumSeaGreen;
133 plotColorPalette[12] = Color.Olive;
134 plotColorPalette[13] = Color.Firebrick;
136 plotMenuItem.Checked = Config.Get(plotMenuItem.Name, false);
137 minMenuItem.Checked = Config.Get(minMenuItem.Name, false);
138 maxMenuItem.Checked = Config.Get(maxMenuItem.Name, true);
139 limitMenuItem.Checked = Config.Get(limitMenuItem.Name, false);
141 startMinMenuItem.Checked = Config.Get(startMinMenuItem.Name, false);
142 minTrayMenuItem.Checked = Config.Get(minTrayMenuItem.Name, true);
143 startupMenuItem.Checked = startupManager.Startup;
144 hddMenuItem.Checked = Config.Get(hddMenuItem.Name, true);
146 voltMenuItem.Checked = Config.Get(voltMenuItem.Name, true);
147 clocksMenuItem.Checked = Config.Get(clocksMenuItem.Name, true);
148 loadMenuItem.Checked = Config.Get(loadMenuItem.Name, true);
149 tempMenuItem.Checked = Config.Get(tempMenuItem.Name, true);
150 fansMenuItem.Checked = Config.Get(fansMenuItem.Name, true);
151 flowsMenuItem.Checked = Config.Get(flowsMenuItem.Name, true);
153 if (startMinMenuItem.Checked) {
154 if (!minTrayMenuItem.Checked) {
155 WindowState = FormWindowState.Minimized;
162 // Create a handle, otherwise calling Close() does not fire FormClosed
163 IntPtr handle = Handle;
166 private void SubHardwareAdded(IHardware hardware, Node node) {
167 Node hardwareNode = new HardwareNode(hardware);
168 node.Nodes.Add(hardwareNode);
169 foreach (IHardware subHardware in hardware.SubHardware)
170 SubHardwareAdded(subHardware, hardwareNode);
173 private void HardwareAdded(IHardware hardware) {
174 Node hardwareNode = new HardwareNode(hardware);
175 root.Nodes.Add(hardwareNode);
176 foreach (IHardware subHardware in hardware.SubHardware)
177 SubHardwareAdded(subHardware, hardwareNode);
180 private void HardwareRemoved(IHardware hardware) {
181 List<Node> nodesToRemove = new List<Node>();
182 foreach (Node node in root.Nodes) {
183 HardwareNode hardwareNode = node as HardwareNode;
184 if (hardwareNode != null && hardwareNode.Hardware == hardware)
185 nodesToRemove.Add(node);
187 foreach (Node node in nodesToRemove)
188 root.Nodes.Remove(node);
191 private void nodeTextBoxLimit_DrawText(object sender, DrawEventArgs e) {
192 SensorNode sensorNode = e.Node.Tag as SensorNode;
193 if (sensorNode != null)
194 e.Text = sensorNode.ValueToString(sensorNode.Sensor.Limit);
197 private void nodeTextBoxText_DrawText(object sender, DrawEventArgs e) {
198 if (!plotMenuItem.Checked)
201 SensorNode sensorNode = e.Node.Tag as SensorNode;
202 if (sensorNode != null) {
204 if (sensorPlotColors.TryGetValue(sensorNode.Sensor, out color))
209 private void UpdatePlotSelection(object sender,
212 List<ISensor> selected = new List<ISensor>();
213 IDictionary<ISensor, Color> colors = new Dictionary<ISensor, Color>();
215 foreach (TreeNodeAdv node in treeView.AllNodes) {
216 SensorNode sensorNode = node.Tag as SensorNode;
217 if (sensorNode != null &&
218 sensorNode.Sensor.SensorType == SensorType.Temperature) {
219 if (sensorNode.Plot) {
220 colors.Add(sensorNode.Sensor,
221 plotColorPalette[colorIndex % plotColorPalette.Length]);
222 selected.Add(sensorNode.Sensor);
227 sensorPlotColors = colors;
228 plotPanel.SetSensors(selected, colors);
231 private void nodeCheckBox_IsVisibleValueNeeded(object sender,
232 NodeControlValueEventArgs e) {
233 SensorNode node = e.Node.Tag as SensorNode;
234 e.Value = (node != null) &&
235 (node.Sensor.SensorType == SensorType.Temperature) &&
236 plotMenuItem.Checked;
239 private void exitToolStripMenuItem_Click(object sender, EventArgs e) {
243 private void timer_Tick(object sender, EventArgs e) {
245 treeView.Invalidate();
246 plotPanel.Invalidate();
247 sensorSystemTray.Redraw();
250 private void MainForm_FormClosed(object sender, FormClosedEventArgs e) {
252 Config.Set(plotMenuItem.Name, plotMenuItem.Checked);
253 Config.Set(minMenuItem.Name, minMenuItem.Checked);
254 Config.Set(maxMenuItem.Name, maxMenuItem.Checked);
255 Config.Set(limitMenuItem.Name, limitMenuItem.Checked);
257 Config.Set(startMinMenuItem.Name, startMinMenuItem.Checked);
258 Config.Set(minTrayMenuItem.Name, minTrayMenuItem.Checked);
259 Config.Set(hddMenuItem.Name, hddMenuItem.Checked);
261 Config.Set(voltMenuItem.Name, voltMenuItem.Checked);
262 Config.Set(clocksMenuItem.Name, clocksMenuItem.Checked);
263 Config.Set(loadMenuItem.Name, loadMenuItem.Checked);
264 Config.Set(tempMenuItem.Name, tempMenuItem.Checked);
265 Config.Set(fansMenuItem.Name, fansMenuItem.Checked);
266 Config.Set(flowsMenuItem.Name, flowsMenuItem.Checked);
268 if (WindowState != FormWindowState.Minimized) {
269 Config.Set("mainForm.Location.X", Location.X);
270 Config.Set("mainForm.Location.Y", Location.Y);
271 Config.Set("mainForm.Width", Width);
272 Config.Set("mainForm.Height", Height);
275 timer.Enabled = false;
277 sensorSystemTray.Dispose();
278 notifyIcon.Dispose();
282 private void aboutToolStripMenuItem_Click(object sender, EventArgs e) {
283 new AboutBox().ShowDialog();
286 private void plotToolStripMenuItem_CheckedChanged(object sender,
289 splitContainer.Panel2Collapsed = !plotMenuItem.Checked;
290 treeView.Invalidate();
293 private void valueToolStripMenuItem_CheckedChanged(object sender,
296 treeView.Columns[1].IsVisible = valueToolStripMenuItem.Checked;
299 private void minToolStripMenuItem_CheckedChanged(object sender, EventArgs e)
301 treeView.Columns[2].IsVisible = minMenuItem.Checked;
304 private void maxToolStripMenuItem_CheckedChanged(object sender, EventArgs e)
306 treeView.Columns[3].IsVisible = maxMenuItem.Checked;
309 private void limitToolStripMenuItem_CheckedChanged(object sender,
311 treeView.Columns[4].IsVisible = limitMenuItem.Checked;
314 private void treeView_Click(object sender, EventArgs e) {
316 MouseEventArgs m = e as MouseEventArgs;
317 if (m == null || m.Button != MouseButtons.Right)
320 NodeControlInfo info = treeView.GetNodeControlInfoAt(new Point(m.X, m.Y));
321 if (info.Control == null) {
322 columnsContextMenuStrip.Show(treeView, m.X, m.Y);
324 SensorNode node = info.Node.Tag as SensorNode;
325 if (node != null && node.Sensor != null) {
327 sensorContextMenuStrip.Items.Clear();
328 if (node.Sensor.Parameters.Length > 0) {
329 ToolStripMenuItem item = new ToolStripMenuItem("Parameters...");
330 item.Click += delegate(object obj, EventArgs args) {
331 ShowParameterForm(node.Sensor);
333 sensorContextMenuStrip.Items.Add(item);
335 if (sensorSystemTray.Contains(node.Sensor)) {
336 ToolStripMenuItem item = new ToolStripMenuItem("Remove From Tray");
337 item.Click += delegate(object obj, EventArgs args) {
338 sensorSystemTray.Remove(node.Sensor);
340 sensorContextMenuStrip.Items.Add(item);
342 ToolStripMenuItem item = new ToolStripMenuItem("Add To Tray");
343 item.Click += delegate(object obj, EventArgs args) {
344 sensorSystemTray.Add(node.Sensor, true);
346 sensorContextMenuStrip.Items.Add(item);
348 sensorContextMenuStrip.Show(treeView, m.X, m.Y);
353 private void saveReportToolStripMenuItem_Click(object sender, EventArgs e) {
354 string report = computer.GetReport();
355 if (saveFileDialog.ShowDialog() == DialogResult.OK) {
356 using (TextWriter w = new StreamWriter(saveFileDialog.FileName)) {
362 private void hddsensorsToolStripMenuItem_CheckedChanged(object sender,
365 computer.HDDEnabled = hddMenuItem.Checked;
366 UpdateSensorTypeChecked(null, null);
367 UpdatePlotSelection(null, null);
370 private void UpdateSensorTypeVisible(Node node) {
371 HardwareNode hardwareNode = node as HardwareNode;
372 if (hardwareNode == null)
375 hardwareNode.SetVisible(SensorType.Voltage, voltMenuItem.Checked);
376 hardwareNode.SetVisible(SensorType.Clock, clocksMenuItem.Checked);
377 hardwareNode.SetVisible(SensorType.Load, loadMenuItem.Checked);
378 hardwareNode.SetVisible(SensorType.Temperature, tempMenuItem.Checked);
379 hardwareNode.SetVisible(SensorType.Fan, fansMenuItem.Checked);
380 hardwareNode.SetVisible(SensorType.Flow, flowsMenuItem.Checked);
382 foreach (Node n in node.Nodes)
383 UpdateSensorTypeVisible(n);
386 private void UpdateSensorTypeChecked(object sender, EventArgs e) {
387 foreach (HardwareNode node in root.Nodes)
388 UpdateSensorTypeVisible(node);
391 private void SysTrayHideShow() {
397 protected override void WndProc(ref Message m) {
398 const int WM_SYSCOMMAND = 0x112;
399 const int SC_MINIMIZE = 0xF020;
400 if (minTrayMenuItem.Checked &&
401 m.Msg == WM_SYSCOMMAND && m.WParam.ToInt32() == SC_MINIMIZE) {
408 private void hideShowClick(object sender, EventArgs e) {
412 private void removeToolStripMenuItem_Click(object sender, EventArgs e) {
413 ToolStripMenuItem item = sender as ToolStripMenuItem;
417 ISensor sensor = item.Owner.Tag as ISensor;
421 sensorSystemTray.Remove(sensor);
424 private void ShowParameterForm(ISensor sensor) {
425 ParameterForm form = new ParameterForm();
426 form.Parameters = sensor.Parameters;
427 form.captionLabel.Text = sensor.Name;
431 private void treeView_NodeMouseDoubleClick(object sender,
432 TreeNodeAdvMouseEventArgs e) {
433 SensorNode node = e.Node.Tag as SensorNode;
434 if (node != null && node.Sensor != null &&
435 node.Sensor.Parameters.Length > 0) {
436 ShowParameterForm(node.Sensor);
440 private void runOnWindowsStartupToolStripMenuItem_CheckedChanged(
441 object sender, EventArgs e)
443 startupManager.Startup = startupMenuItem.Checked;
446 private void minTrayMenuItem_CheckedChanged(object sender, EventArgs e) {
447 notifyIcon.Visible = minTrayMenuItem.Checked;