MwBakker
MwBakker

Reputation: 495

c# how to correctly align number in DataGrid

I have a working Windows Forms application that loads in transaction-data and categorizes it, adding the amount of euros spent on that certain category.

The amount of euros is shown in the dataTable as follows:

cells

but I want the correct alignment when it comes to representing numbers. So this is what I mean:

enter image description here

Now I know a devious way to dealing with this problem (since: how should a dataTable-object itself know how to align to my wishes?)

possible solution

But I would like to know if there is a better approach for this situation.

Upvotes: 1

Views: 1683

Answers (3)

m1kael
m1kael

Reputation: 2851

I'm assuming it's Windows Forms application.

Below is a sample app with a DataGrid with 2 columns, one of which has its values right-aligned. The essential line here is

Alignment = HorizontalAlignment.Right

The app (copy/paste and run it to see the result):

using System.Data;
using System.Drawing;
using System.Windows.Forms;

public class Form1 : System.Windows.Forms.Form
{
    public static void Main()
    {
        Application.Run(new Form1());
    }

    public Form1()
    {
        var myDataGrid = new DataGrid();
        ClientSize = new System.Drawing.Size(450, 330);
        myDataGrid.Location = new Point(24, 50);
        myDataGrid.Size = new Size(300, 200);

        Controls.Add(myDataGrid);

        myDataGrid.SetDataBinding(MakeDataSet(), "MyTable");

        var tableStyle = new DataGridTableStyle { MappingName = "MyTable" };
        var nameColumnStyle = new DataGridTextBoxColumn { MappingName = "Name" };
        var sumColumnStyle = new DataGridTextBoxColumn
        {
            MappingName = "Sum",
            Width = 170,
            Alignment = HorizontalAlignment.Right
        };
        tableStyle.GridColumnStyles.Add(nameColumnStyle);
        tableStyle.GridColumnStyles.Add(sumColumnStyle);
        myDataGrid.TableStyles.Add(tableStyle);
    }

    private DataSet MakeDataSet()
    {
        var dataSet = new DataSet("myDataSet");
        var table = new DataTable("MyTable");
        var nameCol = new DataColumn("Name");
        var sumCol = new DataColumn("Sum", typeof(float));
        table.Columns.Add(nameCol);
        table.Columns.Add(sumCol);

        dataSet.Tables.Add(table);

        var row1 = table.NewRow();
        row1["Name"] = "Bank";
        row1["Sum"] = 1.25;
        table.Rows.Add(row1);

        var row2 = table.NewRow();
        row2["Name"] = "Hosting";
        row2["Sum"] = 12.5;
        table.Rows.Add(row2);

        return dataSet;
    }
}

UPDATE

Here's an example of the custom alignment you need, it's a console app but the same code will work in a Windows Forms app:

    class Program
    {
        static void Main(string[] args)
        {
            var numbers = new[] { 1, 100.12, 50.218, 0.5 };
            int length = 10;
            var separator = CultureInfo.CurrentCulture.NumberFormat.NumberDecimalSeparator;

            foreach (var n in numbers.Select(i => i.ToString()))
            {
                var offset = n.Contains(separator) ? n.Length - n.IndexOf(separator) : 0;
                string format = string.Format("{{0, {0}}}", length + offset);
                Console.WriteLine(string.Format(format, n));
            }
        }
    }

Tweak the variable length to your needs.

Upvotes: 1

Daniel Vinagre
Daniel Vinagre

Reputation: 36

I'm assuming it's a web application in ASP.NET

if you want to right align your numbers use this

<asp:BoundColumn DataField="Value" HeaderText="Value" ItemStyle-HorizontalAlign="Right" DataFormatString="{0:#,##0.00}" ItemStyle-Width="100px"></asp:BoundColumn>

If you want the number to be as close to the left margin as bigger the number is use this

<asp:BoundColumn DataField="ValueString" HeaderText="ValueString" ItemStyle-Width="300px"></asp:BoundColumn>

For this to work you have to have an extra column in your data source with the string representation of your value in wich you will insert various space characters before the number.

Here is an example of how you can manipulate your data

    private void BindData()
    {
        List<Data> data = new List<Data>();
        decimal maxValue = 435;

        data.Add(new Data("Familie", 435m));
        data.Add(new Data("Bank", 1.25m));
        data.Add(new Data("Hosting", 12.1m));

        for (int i = 0; i < data.Count; i++)
        {
            Data item = data[i];
            item.ValueString = buildSpaces(100 - (int)((item.Value / maxValue) * 100)) + item.Value.ToString();
        }
        dg.DataSource = data;
        dg.DataBind();
    }

    private string buildSpaces(int number)
    {
        System.Text.StringBuilder sb = new System.Text.StringBuilder();
        for (int i = 0; i < number; i++)
            sb.Append("&nbsp;");
        return sb.ToString();
    }

Your Data class would be something like this

     public class Data
    {
        public string Name { get; set; }
        public decimal Value { get; set; }
        public string ValueString { get; set; }

        public Data()
        {

        }
        public Data(string name, decimal value)
        {
            Name = name;
            Value = value;
        }
    }

Upvotes: 1

user7138697
user7138697

Reputation:

You can utilize padLeft:

string euroPart = transactionParts[4].trim('"');
string euroPartFixed;
if(europart.length == 6){
    europartFixed = euroPart.PadLeft(7, ' ')
} else if(europart.length == 5){
   europartFixed = euroPart.PadLeft(6, ' ')
} else if(europart.length == 4){
   europartFixed = euroPart.PadLeft(5, ' ')
}

note that padleft(X, ' ')x must be the size of this string you want to fill

Working example : http://ideone.com/TJlCbE

Upvotes: 1

Related Questions