using System;
using System.Collections.Generic;
using System.Text;
using System.Windows.Forms;
using Microsoft.VisualBasic; // e.g. Interaction.InputBox, MsgBox, MsgBoxResult etc.
using System.Diagnostics;
namespace DeviceMenuTesting{
class FormMenu : ConsoleMenuTesting.MenuSystem
{
volatile bool _disposed;
TextBox tb;
Label labelPause;
Menu parentMenu;
MenuItem itemUnpause, itemClearConsole;
public FormMenu(TextBox tb, Menu parentMenu, Label labelPause)
{
this.tb = tb;
this.tb.Disposed += new EventHandler(tb_Disposed);
this.labelPause = labelPause;
this.parentMenu = parentMenu;
SetupPauseControls();
}
void tb_Disposed(object sender, EventArgs e)
{
_disposed = true;
}
Dictionary<string, MenuItem> m_subMenus = new Dictionary<string, MenuItem>();
public override void RunMenu()
{
if (this.tb.InvokeRequired)
throw new InvalidOperationException("Must be called from the main thread.");
itemUnpause = new MenuItem();
itemUnpause.Enabled = false;
itemUnpause.Text = "Un-pause";
itemUnpause.Click += Unpause_Click;
this.parentMenu.MenuItems.Add(itemUnpause);
//
itemClearConsole = new MenuItem();
itemClearConsole.Text = "Clear console";
itemClearConsole.Click += ClearConsole_Click;
this.parentMenu.MenuItems.Add(itemClearConsole);
//
ConsoleMenuTesting.Option.console = this;
foreach (ConsoleMenuTesting.Option cur in Options) {
MenuItem item = new MenuItem();
item.Text = cur.name;
item.Click += cur.EventHandlerInvokeOnBackground;
if (cur.SubMenu == null || cur.SubMenu == RootName) {
this.parentMenu.MenuItems.Add(item);
} else {
if (!m_subMenus.ContainsKey(cur.SubMenu)) {
MenuItem newSubMenu = new MenuItem();
newSubMenu.Text = cur.SubMenu;
m_subMenus.Add(cur.SubMenu, newSubMenu);
this.parentMenu.MenuItems.Add(newSubMenu);
}
MenuItem subMenu = m_subMenus[cur.SubMenu];
subMenu.MenuItems.Add(item);
}
}//for
}
//--------
const string NewLine = "\r\n";
void SafeAppendText(string txt)
{
EventHandler dlgt = delegate {
tb.Text += txt;
};
SafeInvoke(tb, dlgt);
}
void SafeSetText(string txt)
{
EventHandler dlgt = delegate {
tb.Text = txt;
};
SafeInvoke(tb, dlgt);
}
private void SafeInvoke(Control c, EventHandler dlgt)
{
if (_disposed) {
return;
}
if (c.InvokeRequired) {
c.Invoke(dlgt);
} else {
dlgt.Invoke(c, EventArgs.Empty);
}
}
public /*override*/ void Clear()
{
SafeSetText(string.Empty);
}
public override void WriteLine(string msg)
{
SafeAppendText(msg + NewLine);
}
public override void Write(string msg)
{
SafeAppendText(msg);
}
public override void WriteLine(object arg0)
{
WriteLine(arg0.ToString());
}
public override void WriteLine(string fmt, params object[] args)
{
WriteLine(string.Format(fmt, args));
}
public override void Write(string fmt, params object[] args)
{
Write(string.Format(fmt, args));
}
string SafeReadLine(string prompt, string title)
{
string txt = "eeeeeeh";
EventHandler dlgt = delegate {
txt = Interaction.InputBox(prompt, title,
null, -1, -1);
};
SafeInvoke(this.tb, dlgt);
return txt;
}
MsgBoxResult SafeMsgBox(string prompt, string title,
MsgBoxStyle buttons)
{
MsgBoxResult result = MsgBoxResult.Cancel;
EventHandler dlgt = delegate {
result = Interaction.MsgBox(prompt, buttons,
title);
};
SafeInvoke(this.tb, dlgt);
return result;
}
//--------
public override string ReadLine(string prompt)
{
return SafeReadLine(prompt, "ReadLine");
}
public override int ReadInteger(string prompt)
{
while (true) {
int value;
string txt = SafeReadLine(prompt, "ReadInteger");
value = int.Parse(txt);
return value;
}
}
public override int? ReadOptionalInteger(string prompt)
{
while (true) {
int value;
string txt = SafeReadLine(prompt, "ReadOptionalInteger");
if (string.IsNullOrEmpty(txt)) {
return null;
} else {
value = int.Parse(txt);
return value;
}
}
}
public override int? ReadOptionalIntegerHexadecimal(string prompt)
{
while (true) {
int value;
string txt = SafeReadLine(prompt, "ReadOptionalIntegerHexadecimal");
if (string.IsNullOrEmpty(txt)) {
return null;
} else {
value = int.Parse(txt, System.Globalization.NumberStyles.HexNumber);
return value;
}
}
}
public override InTheHand.Net.BluetoothAddress ReadBluetoothAddress(string prompt)
{
while (true) {
InTheHand.Net.BluetoothAddress value;
string txt = SafeReadLine(prompt, "ReadBluetoothAddress");
if (InTheHand.Net.BluetoothAddress.TryParse(txt, out value))
return value;
}
}
void ClearConsole_Click(object sender, EventArgs e)
{
Clear();
}
System.Threading.ManualResetEvent m_pause = new System.Threading.ManualResetEvent(false);
public override void Pause(string prompt)
{
m_pause.Reset();
ShowPause(true, prompt);
bool x = m_pause.WaitOne();
}
private void Unpause_Click(object sender, EventArgs e)
{
ShowPause(false, null);
m_pause.Set();
}
private void SetupPauseControls()
{
this.labelPause.SendToBack();
ShowPause(false, null);
}
private void ShowPause(bool pausing, string prompt)
{
System.Threading.ThreadStart dlgt = delegate {
if (pausing) {
WriteLine(prompt);
this.labelPause.Text = "Menu->Un-pause: " + prompt;
this.labelPause.Visible = true;
Debug.Assert(itemUnpause != null, "init'd in RunMenu so should be valid!");
} else {
this.labelPause.Visible = false;
}
if (itemUnpause != null) {
itemUnpause.Enabled = pausing;
}
};
if (this.tb.InvokeRequired) {
this.tb.BeginInvoke(dlgt);
} else {
dlgt();
}
}
void Pause__old()
{
//bool hc = this.tb.IsHandleCreated;
bool ir = this.tb.InvokeRequired;
if (ir) { //DEBUG
}
MessageBox.Show("Pause" + (ir ? " InvokeRequired!!" : " (is on UI thread)"), "Pause",
MessageBoxButtons.OK, MessageBoxIcon.Hand, MessageBoxDefaultButton.Button1);
}
public override bool ReadYesNo(string prompt, bool defaultYes)
{
MsgBoxStyle style = MsgBoxStyle.YesNo;
style |= (defaultYes ? MsgBoxStyle.DefaultButton1 : MsgBoxStyle.DefaultButton2);
while (true) {
MsgBoxResult val = SafeMsgBox(prompt, "ReadYesNo", style);
Debug.Assert(val == MsgBoxResult.Yes || val == MsgBoxResult.No);
return (val == MsgBoxResult.Yes); // true==Yes, false==No
}
}
public override Guid? ReadOptionalBluetoothUuid(string prompt)
{
while (true) {
Guid value;
string txt = SafeReadLine(prompt, "ReadOptionalIntegerHexadecimal");
if (string.IsNullOrEmpty(txt)) {
return null;
} else {
if(base.BluetoothService_TryParseIncludingShortForm(txt, out value))
return value;
// Continue to give user another chance to input a good value.
}
}
}
private void Log(string msg)
{
SafeAppendText(msg + "\r\n");
}
//--
public override void UiInvoke(EventHandler dlgt)
{
SafeInvoke(tb, dlgt);
}
}
}
|