Browse Source

Merge pull request #2203 from BDisp/csv-editor-fix

Fixes #2195. CsvEditor: Column Type dialog not wide enough.
Tig 2 years ago
parent
commit
254b26a13d

+ 7 - 2
Terminal.Gui/Views/ComboBox.cs

@@ -749,7 +749,7 @@ namespace Terminal.Gui {
 			}
 			}
 
 
 			SetValue (searchset [listview.SelectedItem]);
 			SetValue (searchset [listview.SelectedItem]);
-			search.CursorPosition = search.Text.RuneCount;
+			search.CursorPosition = search.Text.ConsoleWidth;
 			Search_Changed (search.Text);
 			Search_Changed (search.Text);
 			OnOpenSelectedItem ();
 			OnOpenSelectedItem ();
 			Reset (keepSearchText: true);
 			Reset (keepSearchText: true);
@@ -825,7 +825,12 @@ namespace Terminal.Gui {
 				}
 				}
 			}
 			}
 
 
-			ShowList ();
+			if (HasFocus) {
+				ShowList ();
+			} else if (autoHide) {
+				isShow = false;
+				HideList ();
+			}
 		}
 		}
 
 
 		/// <summary>
 		/// <summary>

+ 7 - 3
Terminal.Gui/Windows/Dialog.cs

@@ -20,7 +20,7 @@ namespace Terminal.Gui {
 	///  or buttons added to the dialog calls <see cref="Application.RequestStop"/>.
 	///  or buttons added to the dialog calls <see cref="Application.RequestStop"/>.
 	/// </remarks>
 	/// </remarks>
 	public class Dialog : Window {
 	public class Dialog : Window {
-		List<Button> buttons = new List<Button> ();
+		internal List<Button> buttons = new List<Button> ();
 		const int padding = 0;
 		const int padding = 0;
 
 
 		/// <summary>
 		/// <summary>
@@ -164,7 +164,11 @@ namespace Terminal.Gui {
 				for (int i = buttons.Count - 1; i >= 0; i--) {
 				for (int i = buttons.Count - 1; i >= 0; i--) {
 					Button button = buttons [i];
 					Button button = buttons [i];
 					shiftLeft += button.Frame.Width + (i == buttons.Count - 1 ? 0 : 1);
 					shiftLeft += button.Frame.Width + (i == buttons.Count - 1 ? 0 : 1);
-					button.X = Pos.AnchorEnd (shiftLeft);
+					if (shiftLeft > -1) {
+						button.X = Pos.AnchorEnd (shiftLeft);
+					} else {
+						button.X = Frame.Width - shiftLeft;
+					}
 					button.Y = Pos.AnchorEnd (1);
 					button.Y = Pos.AnchorEnd (1);
 				}
 				}
 				break;
 				break;
@@ -173,7 +177,7 @@ namespace Terminal.Gui {
 				// Justify Buttons
 				// Justify Buttons
 				// leftmost and rightmost buttons are hard against edges. The rest are evenly spaced.
 				// leftmost and rightmost buttons are hard against edges. The rest are evenly spaced.
 
 
-				var spacing = (int)Math.Ceiling ((double)(Bounds.Width - buttonsWidth - 2) / (buttons.Count - 1));
+				var spacing = (int)Math.Ceiling ((double)(Bounds.Width - buttonsWidth - (Border.DrawMarginFrame ? 2 : 0)) / (buttons.Count - 1));
 				for (int i = buttons.Count - 1; i >= 0; i--) {
 				for (int i = buttons.Count - 1; i >= 0; i--) {
 					Button button = buttons [i];
 					Button button = buttons [i];
 					if (i == buttons.Count - 1) {
 					if (i == buttons.Count - 1) {

+ 27 - 6
Terminal.Gui/Windows/FileDialog.cs

@@ -662,12 +662,17 @@ namespace Terminal.Gui {
 				X = Pos.Right (nameEntry) + 2,
 				X = Pos.Right (nameEntry) + 2,
 				Y = Pos.Top (nameEntry),
 				Y = Pos.Top (nameEntry),
 				Width = Dim.Fill (1),
 				Width = Dim.Fill (1),
-				Height = allowedTypes != null ? allowedTypes.Count + 1 : 1,
+				Height = SetComboBoxHeight (allowedTypes),
 				Text = allowedTypes?.Count > 0 ? allowedTypes [0] : string.Empty,
 				Text = allowedTypes?.Count > 0 ? allowedTypes [0] : string.Empty,
-				ReadOnly = true
+				SelectedItem = allowedTypes?.Count > 0 ? 0 : -1,
+				ReadOnly = true,
+				HideDropdownListOnClick = true
 			};
 			};
 			cmbAllowedTypes.SetSource (allowedTypes ?? new List<string> ());
 			cmbAllowedTypes.SetSource (allowedTypes ?? new List<string> ());
-			cmbAllowedTypes.OpenSelectedItem += (e) => AllowedFileTypes = cmbAllowedTypes.Text.ToString ().Split (';');
+			cmbAllowedTypes.OpenSelectedItem += (e) => {
+				dirListView.AllowedFileTypes = cmbAllowedTypes.Text.ToString ().Split (';');
+				dirListView.Reload ();
+			};
 			Add (cmbAllowedTypes);
 			Add (cmbAllowedTypes);
 
 
 			dirListView = new DirListView (this) {
 			dirListView = new DirListView (this) {
@@ -679,7 +684,7 @@ namespace Terminal.Gui {
 			DirectoryPath = Path.GetFullPath (Environment.CurrentDirectory);
 			DirectoryPath = Path.GetFullPath (Environment.CurrentDirectory);
 			Add (dirListView);
 			Add (dirListView);
 
 
-			AllowedFileTypes = cmbAllowedTypes.Text.ToString ().Split (';');
+			AllowedFileTypes = allowedTypes?.Count > 0 ? allowedTypes?.ToArray () : null;
 			dirListView.DirectoryChanged = (dir) => { nameEntry.Text = ustring.Empty; dirEntry.Text = dir; };
 			dirListView.DirectoryChanged = (dir) => { nameEntry.Text = ustring.Empty; dirEntry.Text = dir; };
 			dirListView.FileChanged = (file) => nameEntry.Text = file == ".." ? "" : file;
 			dirListView.FileChanged = (file) => nameEntry.Text = file == ".." ? "" : file;
 			dirListView.SelectedChanged = (file) => nameEntry.Text = file.Item1 == ".." ? "" : file.Item1;
 			dirListView.SelectedChanged = (file) => nameEntry.Text = file.Item1 == ".." ? "" : file.Item1;
@@ -744,6 +749,11 @@ namespace Terminal.Gui {
 			}
 			}
 		}
 		}
 
 
+		private static int SetComboBoxHeight (List<string> allowedTypes)
+		{
+			return allowedTypes != null ? Math.Min (allowedTypes.Count + 1, 8) : 8;
+		}
+
 		internal bool canceled;
 		internal bool canceled;
 
 
 		///<inheritdoc/>
 		///<inheritdoc/>
@@ -827,13 +837,24 @@ namespace Terminal.Gui {
 			}
 			}
 		}
 		}
 
 
+		private string [] allowedFileTypes;
+
 		/// <summary>
 		/// <summary>
 		/// The array of filename extensions allowed, or null if all file extensions are allowed.
 		/// The array of filename extensions allowed, or null if all file extensions are allowed.
 		/// </summary>
 		/// </summary>
 		/// <value>The allowed file types.</value>
 		/// <value>The allowed file types.</value>
 		public string [] AllowedFileTypes {
 		public string [] AllowedFileTypes {
-			get => dirListView.AllowedFileTypes;
-			set => dirListView.AllowedFileTypes = value;
+			get => allowedFileTypes;
+			set {
+				allowedFileTypes = value;
+				var selected = cmbAllowedTypes.SelectedItem;
+				cmbAllowedTypes.SetSource (value);
+				cmbAllowedTypes.SelectedItem = selected > -1 ? selected : 0;
+				SetComboBoxHeight (value?.ToList ());
+				dirListView.AllowedFileTypes = value != null
+					? value [cmbAllowedTypes.SelectedItem].Split (';')
+					: null;
+			}
 		}
 		}
 
 
 		/// <summary>
 		/// <summary>

+ 1 - 1
Terminal.Gui/Windows/MessageBox.cs

@@ -303,7 +303,7 @@ namespace Terminal.Gui {
 
 
 			if (width == 0 & height == 0) {
 			if (width == 0 & height == 0) {
 				// Dynamically size Width
 				// Dynamically size Width
-				d.Width = Math.Min (Math.Max (maxWidthLine, Math.Max (title.ConsoleWidth, Math.Max (textWidth + 2, d.GetButtonsWidth ()))), Application.Driver.Cols); // textWidth + (left + padding + padding + right)
+				d.Width = Math.Min (Math.Max (maxWidthLine, Math.Max (title.ConsoleWidth, Math.Max (textWidth + 2, d.GetButtonsWidth () + d.buttons.Count + 2))), Application.Driver.Cols); // textWidth + (left + padding + padding + right)
 			}
 			}
 
 
 			// Setup actions
 			// Setup actions

+ 183 - 188
UICatalog/Scenarios/CsvEditor.cs

@@ -20,8 +20,7 @@ namespace UICatalog.Scenarios {
 	[ScenarioCategory ("Dialogs")]
 	[ScenarioCategory ("Dialogs")]
 	[ScenarioCategory ("Top Level Windows")]
 	[ScenarioCategory ("Top Level Windows")]
 	[ScenarioCategory ("Files and IO")]
 	[ScenarioCategory ("Files and IO")]
-	public class CsvEditor : Scenario 
-	{
+	public class CsvEditor : Scenario {
 		TableView tableView;
 		TableView tableView;
 		private string currentFile;
 		private string currentFile;
 		private MenuItem miLeft;
 		private MenuItem miLeft;
@@ -31,7 +30,7 @@ namespace UICatalog.Scenarios {
 
 
 		public override void Setup ()
 		public override void Setup ()
 		{
 		{
-			Win.Title = this.GetName();
+			Win.Title = this.GetName ();
 			Win.Y = 1; // menu
 			Win.Y = 1; // menu
 			Win.Height = Dim.Fill (1); // status bar
 			Win.Height = Dim.Fill (1); // status bar
 			Application.Top.LayoutSubviews ();
 			Application.Top.LayoutSubviews ();
@@ -81,22 +80,22 @@ namespace UICatalog.Scenarios {
 
 
 			Win.Add (tableView);
 			Win.Add (tableView);
 
 
-			selectedCellLabel = new TextField(){
+			selectedCellLabel = new TextField () {
 				X = 0,
 				X = 0,
-				Y = Pos.Bottom(tableView),
+				Y = Pos.Bottom (tableView),
 				Text = "0,0",
 				Text = "0,0",
-				Width = Dim.Fill(),
-				TextAlignment = TextAlignment.Right				
+				Width = Dim.Fill (),
+				TextAlignment = TextAlignment.Right
 			};
 			};
 			selectedCellLabel.TextChanged += SelectedCellLabel_TextChanged;
 			selectedCellLabel.TextChanged += SelectedCellLabel_TextChanged;
 
 
-			Win.Add(selectedCellLabel);
+			Win.Add (selectedCellLabel);
 
 
 			tableView.SelectedCellChanged += OnSelectedCellChanged;
 			tableView.SelectedCellChanged += OnSelectedCellChanged;
 			tableView.CellActivated += EditCurrentCell;
 			tableView.CellActivated += EditCurrentCell;
 			tableView.KeyPress += TableViewKeyPress;
 			tableView.KeyPress += TableViewKeyPress;
 
 
-			SetupScrollBar();
+			SetupScrollBar ();
 		}
 		}
 
 
 		private void SelectedCellLabel_TextChanged (ustring last)
 		private void SelectedCellLabel_TextChanged (ustring last)
@@ -104,10 +103,10 @@ namespace UICatalog.Scenarios {
 			// if user is in the text control and editing the selected cell
 			// if user is in the text control and editing the selected cell
 			if (!selectedCellLabel.HasFocus)
 			if (!selectedCellLabel.HasFocus)
 				return;
 				return;
-			
+
 			// change selected cell to the one the user has typed into the box
 			// change selected cell to the one the user has typed into the box
-			var match = Regex.Match (selectedCellLabel.Text.ToString(), "^(\\d+),(\\d+)$");
-			if(match.Success) {
+			var match = Regex.Match (selectedCellLabel.Text.ToString (), "^(\\d+),(\\d+)$");
+			if (match.Success) {
 
 
 				tableView.SelectedColumn = int.Parse (match.Groups [1].Value);
 				tableView.SelectedColumn = int.Parse (match.Groups [1].Value);
 				tableView.SelectedRow = int.Parse (match.Groups [2].Value);
 				tableView.SelectedRow = int.Parse (match.Groups [2].Value);
@@ -119,149 +118,147 @@ namespace UICatalog.Scenarios {
 			// only update the text box if the user is not manually editing it
 			// only update the text box if the user is not manually editing it
 			if (!selectedCellLabel.HasFocus)
 			if (!selectedCellLabel.HasFocus)
 				selectedCellLabel.Text = $"{tableView.SelectedRow},{tableView.SelectedColumn}";
 				selectedCellLabel.Text = $"{tableView.SelectedRow},{tableView.SelectedColumn}";
-			
-			if(tableView.Table == null || tableView.SelectedColumn == -1)
+
+			if (tableView.Table == null || tableView.SelectedColumn == -1)
 				return;
 				return;
 
 
-			var col = tableView.Table.Columns[tableView.SelectedColumn];
+			var col = tableView.Table.Columns [tableView.SelectedColumn];
+
+			var style = tableView.Style.GetColumnStyleIfAny (col);
 
 
-			var style = tableView.Style.GetColumnStyleIfAny(col);
-			
 			miLeft.Checked = style?.Alignment == TextAlignment.Left;
 			miLeft.Checked = style?.Alignment == TextAlignment.Left;
 			miRight.Checked = style?.Alignment == TextAlignment.Right;
 			miRight.Checked = style?.Alignment == TextAlignment.Right;
-			miCentered.Checked = style?.Alignment == TextAlignment.Centered;			
+			miCentered.Checked = style?.Alignment == TextAlignment.Centered;
 		}
 		}
 
 
 		private void RenameColumn ()
 		private void RenameColumn ()
 		{
 		{
-			if(NoTableLoaded()) {
+			if (NoTableLoaded ()) {
 				return;
 				return;
 			}
 			}
 
 
-			var currentCol = tableView.Table.Columns[tableView.SelectedColumn];
+			var currentCol = tableView.Table.Columns [tableView.SelectedColumn];
 
 
-			if(GetText("Rename Column","Name:",currentCol.ColumnName,out string newName)) {
+			if (GetText ("Rename Column", "Name:", currentCol.ColumnName, out string newName)) {
 				currentCol.ColumnName = newName;
 				currentCol.ColumnName = newName;
-				tableView.Update();
+				tableView.Update ();
 			}
 			}
 		}
 		}
 
 
-		private void DeleteColum()
+		private void DeleteColum ()
 		{
 		{
-			if(NoTableLoaded()) {
+			if (NoTableLoaded ()) {
 				return;
 				return;
 			}
 			}
 
 
-			if(tableView.SelectedColumn == -1) {
-				
-				MessageBox.ErrorQuery("No Column","No column selected", "Ok");
+			if (tableView.SelectedColumn == -1) {
+
+				MessageBox.ErrorQuery ("No Column", "No column selected", "Ok");
 				return;
 				return;
 			}
 			}
 
 
 
 
 			try {
 			try {
-				tableView.Table.Columns.RemoveAt(tableView.SelectedColumn);
-				tableView.Update();
+				tableView.Table.Columns.RemoveAt (tableView.SelectedColumn);
+				tableView.Update ();
 
 
 			} catch (Exception ex) {
 			} catch (Exception ex) {
-				MessageBox.ErrorQuery("Could not remove column",ex.Message, "Ok");
+				MessageBox.ErrorQuery ("Could not remove column", ex.Message, "Ok");
 			}
 			}
 		}
 		}
 
 
 		private void MoveColumn ()
 		private void MoveColumn ()
 		{
 		{
-			if(NoTableLoaded()) {
+			if (NoTableLoaded ()) {
 				return;
 				return;
 			}
 			}
 
 
-			if(tableView.SelectedColumn == -1) {
-				
-				MessageBox.ErrorQuery("No Column","No column selected", "Ok");
+			if (tableView.SelectedColumn == -1) {
+
+				MessageBox.ErrorQuery ("No Column", "No column selected", "Ok");
 				return;
 				return;
 			}
 			}
-			
-			try{
 
 
-				var currentCol = tableView.Table.Columns[tableView.SelectedColumn];
+			try {
+
+				var currentCol = tableView.Table.Columns [tableView.SelectedColumn];
 
 
-				if(GetText("Move Column","New Index:",currentCol.Ordinal.ToString(),out string newOrdinal)) {
+				if (GetText ("Move Column", "New Index:", currentCol.Ordinal.ToString (), out string newOrdinal)) {
 
 
-					var newIdx = Math.Min(Math.Max(0,int.Parse(newOrdinal)),tableView.Table.Columns.Count-1);
+					var newIdx = Math.Min (Math.Max (0, int.Parse (newOrdinal)), tableView.Table.Columns.Count - 1);
 
 
-					currentCol.SetOrdinal(newIdx);
+					currentCol.SetOrdinal (newIdx);
 
 
-					tableView.SetSelection(newIdx,tableView.SelectedRow,false);
-					tableView.EnsureSelectedCellIsVisible();
-					tableView.SetNeedsDisplay();
+					tableView.SetSelection (newIdx, tableView.SelectedRow, false);
+					tableView.EnsureSelectedCellIsVisible ();
+					tableView.SetNeedsDisplay ();
 				}
 				}
 
 
-			}catch(Exception ex)
-			{
-				MessageBox.ErrorQuery("Error moving column",ex.Message, "Ok");
+			} catch (Exception ex) {
+				MessageBox.ErrorQuery ("Error moving column", ex.Message, "Ok");
 			}
 			}
 		}
 		}
 		private void Sort (bool asc)
 		private void Sort (bool asc)
 		{
 		{
 
 
-			if(NoTableLoaded()) {
+			if (NoTableLoaded ()) {
 				return;
 				return;
 			}
 			}
 
 
-			if(tableView.SelectedColumn == -1) {
-				
-				MessageBox.ErrorQuery("No Column","No column selected", "Ok");
+			if (tableView.SelectedColumn == -1) {
+
+				MessageBox.ErrorQuery ("No Column", "No column selected", "Ok");
 				return;
 				return;
 			}
 			}
 
 
-			var colName = tableView.Table.Columns[tableView.SelectedColumn].ColumnName;
+			var colName = tableView.Table.Columns [tableView.SelectedColumn].ColumnName;
 
 
 			tableView.Table.DefaultView.Sort = colName + (asc ? " asc" : " desc");
 			tableView.Table.DefaultView.Sort = colName + (asc ? " asc" : " desc");
-			tableView.Table = tableView.Table.DefaultView.ToTable();
+			tableView.Table = tableView.Table.DefaultView.ToTable ();
 		}
 		}
 
 
 		private void MoveRow ()
 		private void MoveRow ()
 		{
 		{
-			if(NoTableLoaded()) {
+			if (NoTableLoaded ()) {
 				return;
 				return;
 			}
 			}
 
 
-			if(tableView.SelectedRow == -1) {
-				
-				MessageBox.ErrorQuery("No Rows","No row selected", "Ok");
+			if (tableView.SelectedRow == -1) {
+
+				MessageBox.ErrorQuery ("No Rows", "No row selected", "Ok");
 				return;
 				return;
 			}
 			}
-			
-			try{
+
+			try {
 
 
 				int oldIdx = tableView.SelectedRow;
 				int oldIdx = tableView.SelectedRow;
 
 
-				var currentRow = tableView.Table.Rows[oldIdx];
+				var currentRow = tableView.Table.Rows [oldIdx];
 
 
-				if(GetText("Move Row","New Row:",oldIdx.ToString(),out string newOrdinal)) {
+				if (GetText ("Move Row", "New Row:", oldIdx.ToString (), out string newOrdinal)) {
 
 
-					var newIdx = Math.Min(Math.Max(0,int.Parse(newOrdinal)),tableView.Table.Rows.Count-1);
+					var newIdx = Math.Min (Math.Max (0, int.Parse (newOrdinal)), tableView.Table.Rows.Count - 1);
 
 
 
 
-					if(newIdx == oldIdx)
+					if (newIdx == oldIdx)
 						return;
 						return;
 
 
 					var arrayItems = currentRow.ItemArray;
 					var arrayItems = currentRow.ItemArray;
-					tableView.Table.Rows.Remove(currentRow);
+					tableView.Table.Rows.Remove (currentRow);
 
 
 					// Removing and Inserting the same DataRow seems to result in it loosing its values so we have to create a new instance
 					// Removing and Inserting the same DataRow seems to result in it loosing its values so we have to create a new instance
-					var newRow = tableView.Table.NewRow();
+					var newRow = tableView.Table.NewRow ();
 					newRow.ItemArray = arrayItems;
 					newRow.ItemArray = arrayItems;
-					
-					tableView.Table.Rows.InsertAt(newRow,newIdx);
-					
-					tableView.SetSelection(tableView.SelectedColumn,newIdx,false);
-					tableView.EnsureSelectedCellIsVisible();
-					tableView.SetNeedsDisplay();
+
+					tableView.Table.Rows.InsertAt (newRow, newIdx);
+
+					tableView.SetSelection (tableView.SelectedColumn, newIdx, false);
+					tableView.EnsureSelectedCellIsVisible ();
+					tableView.SetNeedsDisplay ();
 				}
 				}
 
 
-			}catch(Exception ex)
-			{
-				MessageBox.ErrorQuery("Error moving column",ex.Message, "Ok");
+			} catch (Exception ex) {
+				MessageBox.ErrorQuery ("Error moving column", ex.Message, "Ok");
 			}
 			}
 		}
 		}
 
 
@@ -271,43 +268,43 @@ namespace UICatalog.Scenarios {
 				return;
 				return;
 			}
 			}
 
 
-			var col = tableView.Table.Columns[tableView.SelectedColumn];
+			var col = tableView.Table.Columns [tableView.SelectedColumn];
 
 
-			var style = tableView.Style.GetOrCreateColumnStyle(col);
+			var style = tableView.Style.GetOrCreateColumnStyle (col);
 			style.Alignment = newAlignment;
 			style.Alignment = newAlignment;
 
 
 			miLeft.Checked = style.Alignment == TextAlignment.Left;
 			miLeft.Checked = style.Alignment == TextAlignment.Left;
 			miRight.Checked = style.Alignment == TextAlignment.Right;
 			miRight.Checked = style.Alignment == TextAlignment.Right;
-			miCentered.Checked = style.Alignment == TextAlignment.Centered;	
-			
-			tableView.Update();
+			miCentered.Checked = style.Alignment == TextAlignment.Centered;
+
+			tableView.Update ();
 		}
 		}
-		
-		private void SetFormat()
+
+		private void SetFormat ()
 		{
 		{
 			if (NoTableLoaded ()) {
 			if (NoTableLoaded ()) {
 				return;
 				return;
 			}
 			}
 
 
-			var col = tableView.Table.Columns[tableView.SelectedColumn];
+			var col = tableView.Table.Columns [tableView.SelectedColumn];
 
 
-			if(col.DataType == typeof(string)) {
-				MessageBox.ErrorQuery("Cannot Format Column","String columns cannot be Formatted, try adding a new column to the table with a date/numerical Type","Ok");
+			if (col.DataType == typeof (string)) {
+				MessageBox.ErrorQuery ("Cannot Format Column", "String columns cannot be Formatted, try adding a new column to the table with a date/numerical Type", "Ok");
 				return;
 				return;
 			}
 			}
 
 
-			var style = tableView.Style.GetOrCreateColumnStyle(col);
+			var style = tableView.Style.GetOrCreateColumnStyle (col);
 
 
-			if(GetText("Format","Pattern:",style.Format ?? "",out string newPattern)) {
+			if (GetText ("Format", "Pattern:", style.Format ?? "", out string newPattern)) {
 				style.Format = newPattern;
 				style.Format = newPattern;
-				tableView.Update();
+				tableView.Update ();
 			}
 			}
 		}
 		}
 
 
 		private bool NoTableLoaded ()
 		private bool NoTableLoaded ()
 		{
 		{
-			if(tableView.Table == null) {
-				MessageBox.ErrorQuery("No Table Loaded","No table has currently be opened","Ok");
+			if (tableView.Table == null) {
+				MessageBox.ErrorQuery ("No Table Loaded", "No table has currently be opened", "Ok");
 				return true;
 				return true;
 			}
 			}
 
 
@@ -316,112 +313,115 @@ namespace UICatalog.Scenarios {
 
 
 		private void AddRow ()
 		private void AddRow ()
 		{
 		{
-			if(NoTableLoaded()) {
+			if (NoTableLoaded ()) {
 				return;
 				return;
 			}
 			}
 
 
-			var newRow = tableView.Table.NewRow();
+			var newRow = tableView.Table.NewRow ();
 
 
-			var newRowIdx = Math.Min(Math.Max(0,tableView.SelectedRow+1),tableView.Table.Rows.Count);
+			var newRowIdx = Math.Min (Math.Max (0, tableView.SelectedRow + 1), tableView.Table.Rows.Count);
 
 
-			tableView.Table.Rows.InsertAt(newRow,newRowIdx);
-			tableView.Update();
+			tableView.Table.Rows.InsertAt (newRow, newRowIdx);
+			tableView.Update ();
 		}
 		}
 
 
 		private void AddColumn ()
 		private void AddColumn ()
 		{
 		{
-			if(NoTableLoaded()) {
+			if (NoTableLoaded ()) {
 				return;
 				return;
 			}
 			}
 
 
-			if(GetText("Enter column name","Name:","",out string colName)) {
+			if (GetText ("Enter column name", "Name:", "", out string colName)) {
 
 
-				var col = new DataColumn(colName);
+				var col = new DataColumn (colName);
 
 
-				var newColIdx = Math.Min(Math.Max(0,tableView.SelectedColumn + 1),tableView.Table.Columns.Count);
-				
-				int result = MessageBox.Query(40,15,"Column Type","Pick a data type for the column",new ustring[]{"Date","Integer","Double","Text","Cancel"});
+				var newColIdx = Math.Min (Math.Max (0, tableView.SelectedColumn + 1), tableView.Table.Columns.Count);
 
 
-				if(result <= -1 || result >= 4)
+				int result = MessageBox.Query ("Column Type", "Pick a data type for the column", new ustring [] { "Date", "Integer", "Double", "Text", "Cancel" });
+
+				if (result <= -1 || result >= 4)
 					return;
 					return;
-				switch(result) {
-					case 0: col.DataType = typeof(DateTime);
-						break;
-					case 1: col.DataType = typeof(int);
-						break;
-					case 2: col.DataType = typeof(double);
-						break;
-					case 3: col.DataType = typeof(string);
-						break;
+				switch (result) {
+				case 0:
+					col.DataType = typeof (DateTime);
+					break;
+				case 1:
+					col.DataType = typeof (int);
+					break;
+				case 2:
+					col.DataType = typeof (double);
+					break;
+				case 3:
+					col.DataType = typeof (string);
+					break;
 				}
 				}
 
 
-				tableView.Table.Columns.Add(col);
-				col.SetOrdinal(newColIdx);
-				tableView.Update();
+				tableView.Table.Columns.Add (col);
+				col.SetOrdinal (newColIdx);
+				tableView.Update ();
 			}
 			}
 
 
-			
-				
+
+
 		}
 		}
 
 
-		private void Save()
+		private void Save ()
 		{
 		{
-			if(tableView.Table == null || string.IsNullOrWhiteSpace(currentFile)) {
-				MessageBox.ErrorQuery("No file loaded","No file is currently loaded","Ok");
+			if (tableView.Table == null || string.IsNullOrWhiteSpace (currentFile)) {
+				MessageBox.ErrorQuery ("No file loaded", "No file is currently loaded", "Ok");
 				return;
 				return;
 			}
 			}
 
 
-			var sb = new StringBuilder();
+			var sb = new StringBuilder ();
 
 
-			sb.AppendLine(string.Join(",",tableView.Table.Columns.Cast<DataColumn>().Select(c=>c.ColumnName)));
+			sb.AppendLine (string.Join (",", tableView.Table.Columns.Cast<DataColumn> ().Select (c => c.ColumnName)));
 
 
-			foreach(DataRow row in tableView.Table.Rows) {
-				sb.AppendLine(string.Join(",",row.ItemArray));
+			foreach (DataRow row in tableView.Table.Rows) {
+				sb.AppendLine (string.Join (",", row.ItemArray));
 			}
 			}
-			
-			File.WriteAllText(currentFile,sb.ToString());
+
+			File.WriteAllText (currentFile, sb.ToString ());
 		}
 		}
 
 
-		private void Open()
+		private void Open ()
 		{
 		{
-			var ofd = new FileDialog("Select File","Open","File","Select a CSV file to open (does not support newlines, escaping etc)");
-			ofd.AllowedFileTypes = new string[]{".csv" };
-
-			Application.Run(ofd);
-			
-			if(!ofd.Canceled && !string.IsNullOrWhiteSpace(ofd.FilePath?.ToString()))
-			{
-				Open(ofd.FilePath.ToString());
+			var ofd = new FileDialog ("Select File", "Open", "File", "Select a CSV file to open (does not support newlines, escaping etc)") {
+				AllowedFileTypes = new string [] { ".csv" }
+			};
+
+			Application.Run (ofd);
+
+			if (!ofd.Canceled && !string.IsNullOrWhiteSpace (ofd.FilePath?.ToString ())) {
+				Open (ofd.FilePath.ToString ());
 			}
 			}
 		}
 		}
-		
-		private void Open(string filename)
+
+		private void Open (string filename)
 		{
 		{
-			
+
 			int lineNumber = 0;
 			int lineNumber = 0;
 			currentFile = null;
 			currentFile = null;
 
 
 			try {
 			try {
-				var dt = new DataTable();
-				var lines = File.ReadAllLines(filename);
-			
-				foreach(var h in lines[0].Split(',')){
-					dt.Columns.Add(h);
+				var dt = new DataTable ();
+				var lines = File.ReadAllLines (filename);
+
+				foreach (var h in lines [0].Split (',')) {
+					dt.Columns.Add (h);
 				}
 				}
-				
 
 
-				foreach(var line in lines.Skip(1)) {
+
+				foreach (var line in lines.Skip (1)) {
 					lineNumber++;
 					lineNumber++;
-					dt.Rows.Add(line.Split(','));
+					dt.Rows.Add (line.Split (','));
 				}
 				}
-				
+
 				tableView.Table = dt;
 				tableView.Table = dt;
-				
+
 				// Only set the current filename if we succesfully loaded the entire file
 				// Only set the current filename if we succesfully loaded the entire file
 				currentFile = filename;
 				currentFile = filename;
-			}
-			catch(Exception ex) {
-				MessageBox.ErrorQuery("Open Failed",$"Error on line {lineNumber}{Environment.NewLine}{ex.Message}","Ok");
+			} catch (Exception ex) {
+				MessageBox.ErrorQuery ("Open Failed", $"Error on line {lineNumber}{Environment.NewLine}{ex.Message}", "Ok");
 			}
 			}
 		}
 		}
 		private void SetupScrollBar ()
 		private void SetupScrollBar ()
@@ -445,45 +445,42 @@ namespace UICatalog.Scenarios {
 			};*/
 			};*/
 
 
 			tableView.DrawContent += (e) => {
 			tableView.DrawContent += (e) => {
-				_scrollBar.Size = tableView.Table?.Rows?.Count ??0;
+				_scrollBar.Size = tableView.Table?.Rows?.Count ?? 0;
 				_scrollBar.Position = tableView.RowOffset;
 				_scrollBar.Position = tableView.RowOffset;
-			//	_scrollBar.OtherScrollBarView.Size = _listView.Maxlength - 1;
-			//	_scrollBar.OtherScrollBarView.Position = _listView.LeftItem;
+				//	_scrollBar.OtherScrollBarView.Size = _listView.Maxlength - 1;
+				//	_scrollBar.OtherScrollBarView.Position = _listView.LeftItem;
 				_scrollBar.Refresh ();
 				_scrollBar.Refresh ();
 			};
 			};
-		
+
 		}
 		}
 
 
 		private void TableViewKeyPress (View.KeyEventEventArgs e)
 		private void TableViewKeyPress (View.KeyEventEventArgs e)
 		{
 		{
-			if(e.KeyEvent.Key == Key.DeleteChar){
+			if (e.KeyEvent.Key == Key.DeleteChar) {
 
 
-				if(tableView.FullRowSelect)
-				{
+				if (tableView.FullRowSelect) {
 					// Delete button deletes all rows when in full row mode
 					// Delete button deletes all rows when in full row mode
-					foreach(int toRemove in tableView.GetAllSelectedCells().Select(p=>p.Y).Distinct().OrderByDescending(i=>i))
-						tableView.Table.Rows.RemoveAt(toRemove);
-				}
-				else{
+					foreach (int toRemove in tableView.GetAllSelectedCells ().Select (p => p.Y).Distinct ().OrderByDescending (i => i))
+						tableView.Table.Rows.RemoveAt (toRemove);
+				} else {
 
 
 					// otherwise set all selected cells to null
 					// otherwise set all selected cells to null
-					foreach(var pt in tableView.GetAllSelectedCells())
-					{
-						tableView.Table.Rows[pt.Y][pt.X] = DBNull.Value;
+					foreach (var pt in tableView.GetAllSelectedCells ()) {
+						tableView.Table.Rows [pt.Y] [pt.X] = DBNull.Value;
 					}
 					}
 				}
 				}
 
 
-				tableView.Update();
+				tableView.Update ();
 				e.Handled = true;
 				e.Handled = true;
 			}
 			}
 		}
 		}
 
 
 		private void ClearColumnStyles ()
 		private void ClearColumnStyles ()
 		{
 		{
-			tableView.Style.ColumnStyles.Clear();
-			tableView.Update();
+			tableView.Style.ColumnStyles.Clear ();
+			tableView.Update ();
 		}
 		}
-			
+
 
 
 		private void CloseExample ()
 		private void CloseExample ()
 		{
 		{
@@ -494,7 +491,7 @@ namespace UICatalog.Scenarios {
 		{
 		{
 			Application.RequestStop ();
 			Application.RequestStop ();
 		}
 		}
-		private bool GetText(string title, string label, string initialText, out string enteredText)
+		private bool GetText (string title, string label, string initialText, out string enteredText)
 		{
 		{
 			bool okPressed = false;
 			bool okPressed = false;
 
 
@@ -504,44 +501,42 @@ namespace UICatalog.Scenarios {
 			cancel.Clicked += () => { Application.RequestStop (); };
 			cancel.Clicked += () => { Application.RequestStop (); };
 			var d = new Dialog (title, 60, 20, ok, cancel);
 			var d = new Dialog (title, 60, 20, ok, cancel);
 
 
-			var lbl = new Label() {
+			var lbl = new Label () {
 				X = 0,
 				X = 0,
 				Y = 1,
 				Y = 1,
 				Text = label
 				Text = label
 			};
 			};
 
 
-			var tf = new TextField()
-				{
-					Text = initialText,
-					X = 0,
-					Y = 2,
-					Width = Dim.Fill()
-				};
-			
-			d.Add (lbl,tf);
-			tf.SetFocus();
+			var tf = new TextField () {
+				Text = initialText,
+				X = 0,
+				Y = 2,
+				Width = Dim.Fill ()
+			};
+
+			d.Add (lbl, tf);
+			tf.SetFocus ();
 
 
 			Application.Run (d);
 			Application.Run (d);
 
 
-			enteredText = okPressed? tf.Text.ToString() : null;
+			enteredText = okPressed ? tf.Text.ToString () : null;
 			return okPressed;
 			return okPressed;
 		}
 		}
 		private void EditCurrentCell (TableView.CellActivatedEventArgs e)
 		private void EditCurrentCell (TableView.CellActivatedEventArgs e)
 		{
 		{
-			if(e.Table == null)
+			if (e.Table == null)
 				return;
 				return;
 
 
-			var oldValue = e.Table.Rows[e.Row][e.Col].ToString();
+			var oldValue = e.Table.Rows [e.Row] [e.Col].ToString ();
 
 
-			if(GetText("Enter new value",e.Table.Columns[e.Col].ColumnName,oldValue, out string newText)) {
+			if (GetText ("Enter new value", e.Table.Columns [e.Col].ColumnName, oldValue, out string newText)) {
 				try {
 				try {
-					e.Table.Rows[e.Row][e.Col] = string.IsNullOrWhiteSpace(newText) ? DBNull.Value : (object)newText;
-				}
-				catch(Exception ex) {
-					MessageBox.ErrorQuery(60,20,"Failed to set text", ex.Message,"Ok");
+					e.Table.Rows [e.Row] [e.Col] = string.IsNullOrWhiteSpace (newText) ? DBNull.Value : (object)newText;
+				} catch (Exception ex) {
+					MessageBox.ErrorQuery (60, 20, "Failed to set text", ex.Message, "Ok");
 				}
 				}
-				
-				tableView.Update();
+
+				tableView.Update ();
 			}
 			}
 		}
 		}
 	}
 	}

+ 1 - 1
UICatalog/Scenarios/Editor.cs

@@ -365,7 +365,7 @@ namespace UICatalog.Scenarios {
 			if (!CanCloseFile ()) {
 			if (!CanCloseFile ()) {
 				return;
 				return;
 			}
 			}
-			var aTypes = new List<string> () { ".txt;.bin;.xml;.json", ".txt", ".bin", ".xml", ".*" };
+			var aTypes = new List<string> () { ".txt;.bin;.xml;.json", ".txt", ".bin", ".xml", ".json", ".*" };
 			var d = new OpenDialog ("Open", "Choose the path where to open the file.", aTypes) { AllowsMultipleSelection = false };
 			var d = new OpenDialog ("Open", "Choose the path where to open the file.", aTypes) { AllowsMultipleSelection = false };
 			Application.Run (d);
 			Application.Run (d);
 
 

+ 83 - 21
UnitTests/DialogTests.cs

@@ -142,15 +142,15 @@ namespace Terminal.Gui.Views {
 			Dialog dlg = null;
 			Dialog dlg = null;
 			Button button1, button2;
 			Button button1, button2;
 
 
-			//// Default (Center)
-			//button1 = new Button (btn1Text);
-			//button2 = new Button (btn2Text);
-			//(runstate, dlg) = RunButtonTestDialog (title, width, Dialog.ButtonAlignments.Center, button1, button2);
-			//button1.Visible = false;
-			//Application.RunMainLoopIteration (ref runstate, true, ref firstIteration);
-			//buttonRow = $@"{d.VLine}         {btn2} {d.VLine}";
-			//DriverAsserts.AssertDriverContentsWithFrameAre ($"{topRow}\n{buttonRow}\n{bottomRow}", output);
-			//Application.End (runstate);
+			// Default (Center)
+			button1 = new Button (btn1Text);
+			button2 = new Button (btn2Text);
+			(runstate, dlg) = RunButtonTestDialog (title, width, Dialog.ButtonAlignments.Center, button1, button2);
+			button1.Visible = false;
+			Application.RunMainLoopIteration (ref runstate, true, ref firstIteration);
+			buttonRow = $@"{d.VLine}         {btn2} {d.VLine}";
+			TestHelpers.AssertDriverContentsWithFrameAre ($"{topRow}\n{buttonRow}\n{bottomRow}", output);
+			Application.End (runstate);
 
 
 			// Justify
 			// Justify
 			Assert.Equal (width, buttonRow.Length);
 			Assert.Equal (width, buttonRow.Length);
@@ -163,19 +163,26 @@ namespace Terminal.Gui.Views {
 			TestHelpers.AssertDriverContentsWithFrameAre ($"{topRow}\n{buttonRow}\n{bottomRow}", output);
 			TestHelpers.AssertDriverContentsWithFrameAre ($"{topRow}\n{buttonRow}\n{bottomRow}", output);
 			Application.End (runstate);
 			Application.End (runstate);
 
 
-			//// Right
-			//buttonRow = $@"{d.VLine}  {btn1} {btn2}{d.VLine}";
-			//Assert.Equal (width, buttonRow.Length);
-			//(runstate, dlg) = RunButtonTestDialog (title, width, Dialog.ButtonAlignments.Right, new Button (btn1Text), new Button (btn2Text));
-			//DriverAsserts.AssertDriverContentsWithFrameAre ($"{topRow}\n{buttonRow}\n{bottomRow}", output);
-			//Application.End (runstate);
+			// Right
+			Assert.Equal (width, buttonRow.Length);
+			button1 = new Button (btn1Text);
+			button2 = new Button (btn2Text);
+			(runstate, dlg) = RunButtonTestDialog (title, width, Dialog.ButtonAlignments.Right, button1, button2);
+			button1.Visible = false;
+			Application.RunMainLoopIteration (ref runstate, true, ref firstIteration);
+			TestHelpers.AssertDriverContentsWithFrameAre ($"{topRow}\n{buttonRow}\n{bottomRow}", output);
+			Application.End (runstate);
 
 
-			//// Left
-			//buttonRow = $@"{d.VLine}{btn1} {btn2}  {d.VLine}";
-			//Assert.Equal (width, buttonRow.Length);
-			//(runstate, dlg) = RunButtonTestDialog (title, width, Dialog.ButtonAlignments.Left, new Button (btn1Text), new Button (btn2Text));
-			//DriverAsserts.AssertDriverContentsWithFrameAre ($"{topRow}\n{buttonRow}\n{bottomRow}", output);
-			//Application.End (runstate);
+			// Left
+			Assert.Equal (width, buttonRow.Length);
+			button1 = new Button (btn1Text);
+			button2 = new Button (btn2Text);
+			(runstate, dlg) = RunButtonTestDialog (title, width, Dialog.ButtonAlignments.Left, button1, button2);
+			button1.Visible = false;
+			Application.RunMainLoopIteration (ref runstate, true, ref firstIteration);
+			buttonRow = $@"{d.VLine}        {btn2}  {d.VLine}";
+			TestHelpers.AssertDriverContentsWithFrameAre ($"{topRow}\n{buttonRow}\n{bottomRow}", output);
+			Application.End (runstate);
 		}
 		}
 
 
 		[Fact]
 		[Fact]
@@ -281,6 +288,61 @@ namespace Terminal.Gui.Views {
 			Application.End (runstate);
 			Application.End (runstate);
 		}
 		}
 
 
+		[Fact]
+		[AutoInitShutdown]
+		public void ButtonAlignment_Four_On_Smaller_Width ()
+		{
+			Application.RunState runstate = null;
+
+			var d = ((FakeDriver)Application.Driver);
+
+			var title = "1234";
+
+			// E.g "|[ yes ][ no ][ maybe ][ never ]|"
+			var btn1Text = "yes";
+			var btn1 = $"{d.LeftBracket} {btn1Text} {d.RightBracket}";
+			var btn2Text = "no";
+			var btn2 = $"{d.LeftBracket} {btn2Text} {d.RightBracket}";
+			var btn3Text = "maybe";
+			var btn3 = $"{d.LeftBracket} {btn3Text} {d.RightBracket}";
+			var btn4Text = "never";
+			var btn4 = $"{d.LeftBracket} {btn4Text} {d.RightBracket}";
+
+			var buttonRow = $"{d.VLine} {btn1} {btn2} {btn3} {btn4} {d.VLine}";
+			var width = buttonRow.Length;
+			var topRow = "34 ───────────────────────────";
+			var bottomRow = "──────────────────────────────";
+			d.SetBufferSize (30, 3);
+
+			// Default - Center
+			buttonRow = $"yes ] {btn2} {btn3} [ never";
+			Assert.NotEqual (width, buttonRow.Length);
+			(runstate, var _) = RunButtonTestDialog (title, width, Dialog.ButtonAlignments.Center, new Button (btn1Text), new Button (btn2Text), new Button (btn3Text), new Button (btn4Text));
+			TestHelpers.AssertDriverContentsWithFrameAre ($"{topRow}\n{buttonRow}\n{bottomRow}", output);
+			Application.End (runstate);
+
+			// Justify
+			buttonRow = $"es ] {btn2}  {btn3}  [ neve";
+			Assert.NotEqual (width, buttonRow.Length);
+			(runstate, var _) = RunButtonTestDialog (title, width, Dialog.ButtonAlignments.Justify, new Button (btn1Text), new Button (btn2Text), new Button (btn3Text), new Button (btn4Text));
+			TestHelpers.AssertDriverContentsWithFrameAre ($"{topRow}\n{buttonRow}\n{bottomRow}", output);
+			Application.End (runstate);
+
+			// Right
+			buttonRow = $" yes ] {btn2} {btn3} [ neve";
+			Assert.NotEqual (width, buttonRow.Length);
+			(runstate, var _) = RunButtonTestDialog (title, width, Dialog.ButtonAlignments.Right, new Button (btn1Text), new Button (btn2Text), new Button (btn3Text), new Button (btn4Text));
+			TestHelpers.AssertDriverContentsWithFrameAre ($"{topRow}\n{buttonRow}\n{bottomRow}", output);
+			Application.End (runstate);
+
+			// Left
+			buttonRow = $"es ] {btn2} {btn3} [ never ";
+			Assert.NotEqual (width, buttonRow.Length);
+			(runstate, var _) = RunButtonTestDialog (title, width, Dialog.ButtonAlignments.Left, new Button (btn1Text), new Button (btn2Text), new Button (btn3Text), new Button (btn4Text));
+			TestHelpers.AssertDriverContentsWithFrameAre ($"{topRow}\n{buttonRow}\n{bottomRow}", output);
+			Application.End (runstate);
+		}
+
 		[Fact]
 		[Fact]
 		[AutoInitShutdown]
 		[AutoInitShutdown]
 		public void ButtonAlignment_Four_Wider ()
 		public void ButtonAlignment_Four_Wider ()