tags:

views:

79

answers:

1

Seems like this would be easy to do, but it appears its not so simple. I have a 2d array of floats or ints and I'd like to display it in a grid like control so it acts similar to Excel in regards to being able to move around with the arrow keys, tab keys, etc. The size of the array will vary. This comes close, but works well only for displaying:

http://stackoverflow.com/questions/276808/how-to-populate-a-wpf-grid-based-on-a-2-dimensional-array

A: 

I also made an answer in the thread you linked

Xaml

<DataGrid Name="c_dataGrid"
          RowHeaderWidth="0"
          ColumnHeaderHeight="0"
          AutoGenerateColumns="True"
          CanUserAddRows="False"
          AutoGeneratingColumn="c_dataGrid_AutoGeneratingColumn"/>

Code behind

private int[,] m_int2DArray = new int[5, 5];

public MainWindow()
{
    InitializeComponent();
    InitializeArray();
    c_dataGrid.ItemsSource = BindingHelper.GetBindable2DArray<int>(m_int2DArray, 5);
}

private void InitializeArray()
{
    for (int i = 0; i < 5; i++)
        for (int j = 0; j < 5; j++)
            m_int2DArray[i, j] = (i * 10 + j);
}

private void c_dataGrid_AutoGeneratingColumn(object sender, DataGridAutoGeneratingColumnEventArgs e)
{
    DataGridTextColumn column = e.Column as DataGridTextColumn;
    Binding binding = column.Binding as Binding;
    binding.Path = new PropertyPath(binding.Path.Path + ".Value");
}

Ref class by Eric Lippert's from this thread.

public class Ref<T>
{
    private readonly Func<T> getter;
    private readonly Action<T> setter;
    public Ref(Func<T> getter, Action<T> setter)
    {
        this.getter = getter;
        this.setter = setter;
    }
    public T Value { get { return getter(); } set { setter(value); } }
}

BindingHelper class

public static class BindingHelper
{
    public static DataView GetBindable2DArray<T>(T[,] array, int size)
    {
        DataTable dataTable = new DataTable();
        for (int i = 0; i < size; i++)
        {
            dataTable.Columns.Add(i.ToString(), typeof(Ref<T>));
        }
        DataView dataView = new DataView(dataTable);
        for (int i = 0; i < size; i++)
        {
            DataRowView dataRowView = dataView.AddNew();
            for (int j = 0; j < size; j++)
            {
                int a = i;
                int b = j;
                Ref<T> refT = new Ref<T>(() => array[a, b], z => { array[a, b] = z; });
                dataRowView[j.ToString()] = refT;
            }
            dataRowView.EndEdit();
        }
        return dataView;
    }
}
Meleak