2011-03-25 54 views

回答

4

如果你看看DataGrid的源代码,你可以看到它捕获关键事件(f.i.来实现功能,比如进入下一行的输入按下)。作为解决方案,我建议实现从DataGrid继承自己的网格,并添加当用户按下输入(或其他)按钮时引发的事件。自己的控制:

public class MyDataGrid : DataGrid 
{ 
     public event EventHandler OnLastRowEnterPressed; 

     protected override void OnKeyDown(KeyEventArgs e) 
     { 
      base.OnKeyDown(e); 
       if (ItemsSource != null 
&& ItemsSource.Cast<object>().Count() - 1 == SelectedIndex 
&& e.Key == Key.Enter) 
      { 
       RaiseLastRowEnterPressed(); 
      } 
     } 

     private void RaiseLastRowEnterPressed() 
     { 
      if (OnLastRowEnterPressed != null) 
       OnLastRowEnterPressed(this, EventArgs.Empty); 
     } 
} 

使用:

ObservableCollection<Foo> source = new ObservableCollection<Foo>() 
            { 
             new Foo(), new Foo(), new Foo(), 
            }; 
myDataGrid.OnLastRowEnterPressed += (s, e) => source.Add(new Foo()); 
myDataGrid.ItemsSource = source; 
+0

以及弗拉基米尔,似乎是最后一行退出后添加新行没有简单/直接的方式。上述解决方案将起作用,但也会在其他重要新闻事件中引发事件的后果。 – 2011-04-04 08:56:19

+0

yeap,我已经在 – 2011-04-04 09:06:34

+0

以上的代码中添加了按下的键的检查,以及我不能将整个解决方案作为注释(注释长度验证)我已经把它作为下面的答案。在'按键'检查时,当我使用它时,我没有在我的日志中看到'Enter'键。 – 2011-04-04 09:13:44

0

您可以使用路由事件概念,其中包含输入/制表键,您可以将新行添加到数据网格控件。

1

以及弗拉基米尔,似乎是最后一行退出后添加新行没有简单/直接的方式。您的解决方案将会发挥作用,但也会在其他重要新闻事件中引发事件的后果。我想出了事件的组合来获得解决方案。

protected override void OnKeyDown(KeyEventArgs e) 
{ 
    base.OnKeyDown(e); 
    addFlag = (e.Key == Key.Tab); 
} 

protected override void OnLostFocus(RoutedEventArgs e) 
{ 
    addFlag = (addFlag && true); 
    base.OnLostFocus(e); 
} 

protected override void OnRowEditEnded(DataGridRowEditEndedEventArgs e) 
{ 
    base.OnRowEditEnded(e); 
    addFlag = (addFlag && IsLastRowSelected); 
    if (addFlag) 
     AddItem(); 
    addFlag = false; 
} 

protected override void OnKeyUp(KeyEventArgs e) 
{    
    base.OnKeyUp(e); 
    addFlag = false; 
} 

protected override void OnSelectionChanged(SelectionChangedEventArgs e) 
{ 
    base.OnSelectionChanged(e); 
    addFlag = false; 
} 

private void AddItem() 
{ 
    if (RaiseAddEvent!= null) 
    { 
     this.Focus(); 
     RaiseAddEvent(this, EventArgs.Empty); 
     this.UpdateLayout(); 
     this.CurrentColumn = this.Columns[0]; 
     this.BeginEdit(); 
    } 
} 
0

我会公开几步。所以让我们开始吧..

1)在这个类的构造函数中声明你的事件。

this.DataGrid1.KeyDown += new KeyEventHandler(DataGrid1_KeyDown); 
you also can it in XAML file. 
...KeyDown="DataGrid1_KeyDown"..... 

2)转到您的keydown事件&线制的代码。

var focusedElement = FocusManager.GetFocusedElement(); 
DataGrid detailsDataGrid = sender as DataGrid; 
int dataGridrows = detailsDataGrid.ItemsSource.OfType<object>().Count(); 
if (e.Key == Key.Tab && (Keyboard.Modifiers & ModifierKeys.Shift) == ModifierKeys.Shift) 
return; 
if (e.Key == Key.Tab) 
try 
{ 
detailsDataGrid.SelectedIndex = row.GetIndex(); 
{ 

itemMaster.TransactionChilds.Add(transactionChild); 
detailsDataGrid.SelectedItem = transactionChild; 
} 
} 

3)由线现在代码行..

DataGridRow row = DataGridRow.GetRowContainingElement(focusedElement as FrameworkElement); 
DataGridColumn column = DataGridColumn.GetColumnContainingElement(focusedElement as FrameworkElement); 
TransactionMaster itemMaster = this.DataFormVoucher.CurrentItem as TransactionMaster; 
decimal serialNumber = 0; 
if (buttonPress == "Modify") 
if (dataGridrows - 1 == detailsDataGrid.SelectedIndex && column.DisplayIndex == 5) 

TransactionChild transactionChild = new TransactionChild()"[None]",DateTime.Now.Date,catch (Exception ex)Console.WriteLine(ex.Message); 

.DataGridChild.KeyDown += new KeyEventHandler(DataGridChild_KeyDown); 

3)现在由明白线的代码线

ⅰ)前3行被用来取一个数据网格的哪一行被选中。

ii)在这种情况下,当新行添加时,我已经使用了Tab键,你也可以改变这个。另外一种情况是,如果用户预置Tab + Shift,那么它会通过(默认为控制焦点)。

iii)然后检查它是否是最后一行&该网格的最后一列,如果是,则添加新行或其他。

IV)来添加一个空白的新行只是通过你的对象(EDMX型号表)

相关问题