diff --git a/Terminal.Gui/Core.cs b/Terminal.Gui/Core.cs
index 5adff8b13..92c03af42 100644
--- a/Terminal.Gui/Core.cs
+++ b/Terminal.Gui/Core.cs
@@ -1264,14 +1264,13 @@ namespace Terminal.Gui {
if (p == PlatformID.Win32NT || p == PlatformID.Win32S || p == PlatformID.Win32Windows)
UseSystemConsole = true;
}
- if (UseSystemConsole){
- Console.WriteLine ("WARNING: This version currently does not support data input yet, working on it");
- Console.ReadLine ();
+ UseSystemConsole = true;
+ if (UseSystemConsole)
Driver = new NetDriver ();
- } else
+ else
Driver = new CursesDriver ();
Driver.Init (TerminalResized);
- MainLoop = new Mono.Terminal.MainLoop ();
+ MainLoop = new Mono.Terminal.MainLoop (Driver is CursesDriver);
SynchronizationContext.SetSynchronizationContext (new MainLoopSyncContext (MainLoop));
Top = Toplevel.Create ();
Current = Top;
diff --git a/Terminal.Gui/Driver.cs b/Terminal.Gui/Driver.cs
index b164cb476..f4e4c59e4 100644
--- a/Terminal.Gui/Driver.cs
+++ b/Terminal.Gui/Driver.cs
@@ -834,21 +834,40 @@ namespace Terminal.Gui {
UpdateOffscreen ();
}
+ bool needMove;
// Current row, and current col, tracked by Move/AddCh only
int ccol, crow;
public override void Move (int col, int row)
{
ccol = col;
crow = row;
+
+ if (Clip.Contains (col, row)) {
+ Console.CursorTop = row;
+ Console.CursorLeft = col;
+ needMove = false;
+ } else {
+ Console.CursorTop = Clip.Y;
+ Console.CursorLeft = Clip.X;
+ needMove = true;
+ }
+
}
public override void AddRune (Rune rune)
{
if (Clip.Contains (ccol, crow)) {
- contents [crow, ccol, 0] = (int) (uint) rune;
+ if (needMove) {
+ Console.CursorLeft = ccol;
+ Console.CursorTop = crow;
+ needMove = false;
+ }
+ contents [crow, ccol, 0] = (int)(uint)rune;
contents [crow, ccol, 1] = currentAttribute;
contents [crow, ccol, 2] = 1;
- }
+ dirtyLine [crow] = true;
+ } else
+ needMove = true;
ccol++;
if (ccol == Cols) {
ccol = 0;
@@ -956,6 +975,8 @@ namespace Terminal.Gui {
int rows = Rows;
int cols = Cols;
+ var savedRow = Console.CursorTop;
+ var savedCol = Console.CursorLeft;
for (int row = 0; row < rows; row++) {
if (!dirtyLine [row])
continue;
@@ -976,6 +997,8 @@ namespace Terminal.Gui {
}
}
}
+ Console.CursorTop = savedRow;
+ Console.CursorLeft = savedCol;
}
public override void StartReportingMouseMoves()
@@ -998,27 +1021,9 @@ namespace Terminal.Gui {
Key MapKey (ConsoleKeyInfo keyInfo)
{
- var key = keyInfo.Key;
- if (key >= ConsoleKey.A && key <= ConsoleKey.Z){
- var delta = key - ConsoleKey.A;
- if (keyInfo.Modifiers == ConsoleModifiers.Control)
- return (Key)((uint)Key.ControlA + delta);
- if (keyInfo.Modifiers == ConsoleModifiers.Alt)
- return (Key) (((uint)Key.AltMask) | ((uint)'A' + delta));
- if (keyInfo.Modifiers == ConsoleModifiers.Shift)
- return (Key)((uint)'A' + delta);
- else
- return (Key)((uint)'a' + delta);
- }
- if (key >= ConsoleKey.F1 && key <= ConsoleKey.F10) {
- var delta = key - ConsoleKey.F1;
-
- return (Key)(ConsoleKey.F1 + delta);
- }
-
- switch (keyInfo.Key){
+ switch (keyInfo.Key) {
case ConsoleKey.Tab:
- return Key.ControlT;
+ return Key.Tab;
case ConsoleKey.Escape:
return Key.Esc;
case ConsoleKey.Home:
@@ -1046,6 +1051,25 @@ namespace Terminal.Gui {
case ConsoleKey.Delete:
return Key.Delete;
}
+
+ var key = keyInfo.Key;
+ if (key >= ConsoleKey.A && key <= ConsoleKey.Z){
+ var delta = key - ConsoleKey.A;
+ if (keyInfo.Modifiers == ConsoleModifiers.Control)
+ return (Key)((uint)Key.ControlA + delta);
+ if (keyInfo.Modifiers == ConsoleModifiers.Alt)
+ return (Key) (((uint)Key.AltMask) | ((uint)'A' + delta));
+ if (keyInfo.Modifiers == ConsoleModifiers.Shift)
+ return (Key)((uint)'A' + delta);
+ else
+ return (Key)((uint)'a' + delta);
+ }
+ if (key >= ConsoleKey.F1 && key <= ConsoleKey.F10) {
+ var delta = key - ConsoleKey.F1;
+
+ return (Key)(ConsoleKey.F1 + delta);
+ }
+
return (Key)(0xffffffff);
}
diff --git a/Terminal.Gui/MonoCurses/mainloop.cs b/Terminal.Gui/MonoCurses/mainloop.cs
index 5ebc63414..daa13231d 100644
--- a/Terminal.Gui/MonoCurses/mainloop.cs
+++ b/Terminal.Gui/MonoCurses/mainloop.cs
@@ -36,8 +36,12 @@ namespace Mono.Terminal {
/// Simple main loop implementation that can be used to monitor
/// file descriptor, run timers and idle handlers.
///
+ ///
+ /// Monitoring of file descriptors is only available on Unix, there
+ /// does not seem to be a way of supporting this on Windows.
+ ///
public class MainLoop {
- static bool useUnix = true;
+ bool useUnix = true;
///
/// Condition on which to wake up from file descriptor activity. These match the Linux/BSD poll definitions.
@@ -82,7 +86,7 @@ namespace Mono.Terminal {
}
Dictionary descriptorWatchers = new Dictionary();
- SortedList timeouts = new SortedList ();
+ SortedList timeouts = new SortedList ();
List> idleHandlers = new List> ();
[StructLayout(LayoutKind.Sequential)]
@@ -107,17 +111,27 @@ namespace Mono.Terminal {
bool poll_dirty = true;
int [] wakeupPipes = new int [2];
static IntPtr ignore = Marshal.AllocHGlobal (1);
-
+
///
/// Default constructor
///
- public MainLoop ()
+ public MainLoop () : this (useUnix: true)
{
- pipe (wakeupPipes);
- AddWatch (wakeupPipes [0], Condition.PollIn, ml => {
- read (wakeupPipes [0], ignore, (IntPtr) 1);
- return true;
- });
+ }
+
+ public MainLoop (bool useUnix)
+ {
+ this.useUnix = useUnix;
+ if (useUnix) {
+ pipe (wakeupPipes);
+ AddWatch (wakeupPipes [0], Condition.PollIn, ml => {
+ read (wakeupPipes [0], ignore, (IntPtr)1);
+ return true;
+ });
+ } else {
+ Thread readThread = new Thread (WindowsKeyReader);
+ readThread.Start ();
+ }
}
void Wakeup ()
@@ -260,7 +274,7 @@ namespace Mono.Terminal {
{
long now = DateTime.UtcNow.Ticks;
var copy = timeouts;
- timeouts = new SortedList ();
+ timeouts = new SortedList ();
foreach (var k in copy.Keys){
var timeout = copy [k];
if (k < now) {
@@ -304,7 +318,7 @@ namespace Mono.Terminal {
{
while (true) {
waitForProbe.WaitOne ();
- var result = Console.ReadKey ();
+ windowsKeyResult = Console.ReadKey ();
keyReady.Set ();
}
}
@@ -322,9 +336,12 @@ namespace Mono.Terminal {
long now = DateTime.UtcNow.Ticks;
if (useUnix) {
int pollTimeout, n;
- if (timeouts.Count > 0)
+ if (timeouts.Count > 0){
pollTimeout = (int)((timeouts.Keys [0] - now) / TimeSpan.TicksPerMillisecond);
- else
+ if (pollTimeout < 0)
+ return true;
+
+ } else
pollTimeout = -1;
if (!wait)
@@ -338,10 +355,21 @@ namespace Mono.Terminal {
ic = idleHandlers.Count;
return n > 0 || timeouts.Count > 0 && ((timeouts.Keys [0] - DateTime.UtcNow.Ticks) < 0) || ic > 0;
} else {
+ int waitTimeout;
+ if (timeouts.Count > 0){
+ waitTimeout = (int)((timeouts.Keys [0] - now) / TimeSpan.TicksPerMillisecond);
+ if (waitTimeout < 0)
+ return true;
+ } else
+ waitTimeout = -1;
+
+ if (!wait)
+ waitTimeout = 0;
+
windowsKeyResult = null;
waitForProbe.Set ();
- keyReady.WaitOne ();
- return false;
+ keyReady.WaitOne (waitTimeout);
+ return windowsKeyResult.HasValue;
}
}
diff --git a/Terminal.Gui/Views/ListView.cs b/Terminal.Gui/Views/ListView.cs
index 31172428f..5f67e6d62 100644
--- a/Terminal.Gui/Views/ListView.cs
+++ b/Terminal.Gui/Views/ListView.cs
@@ -282,7 +282,6 @@ namespace Terminal.Gui {
Driver.AddRune (' ');
else
Source.Render (isSelected, item, 0, row, f.Width);
-
}
}
@@ -361,7 +360,7 @@ namespace Terminal.Gui {
///
public override void PositionCursor()
{
- Driver.Move (0, selected);
+ Move (0, selected-top);
}
public override bool MouseEvent(MouseEvent me)
diff --git a/Terminal.Gui/Views/ScrollView.cs b/Terminal.Gui/Views/ScrollView.cs
index 7551cc756..99b239470 100644
--- a/Terminal.Gui/Views/ScrollView.cs
+++ b/Terminal.Gui/Views/ScrollView.cs
@@ -270,6 +270,7 @@ namespace Terminal.Gui {
contentView.Frame = new Rect (contentOffset, value);
vertical.Size = contentSize.Height;
horizontal.Size = contentSize.Width;
+ SetNeedsDisplay ();
}
}
@@ -286,6 +287,7 @@ namespace Terminal.Gui {
contentView.Frame = new Rect (contentOffset, contentSize);
vertical.Position = Math.Max (0, -contentOffset.Y);
horizontal.Position = Math.Max (0, -contentOffset.X);
+ SetNeedsDisplay ();
}
}