internal static void RemoveContextFromObject(DependencyObject context, TreeGridColumn oldValue) { if (context != null && MSInternal.GetInheritanceContext(oldValue) == context) { MSInternal.ProvideSelfAsInheritanceContext(context, oldValue, null); } }
internal static void ProvideContextForObject(DependencyObject context, TreeGridColumn newValue) { if (context != null) { MSInternal.ProvideSelfAsInheritanceContext(context, newValue, null); } }
//protected override void ClearContainerForItemOverride(DependencyObject element, object item) //{ // var cell = element as TreeGridCell; // base.ClearContainerForItemOverride(element, item); // this.ReserveEditingContent(cell); //} //private void ReserveEditingContent(TreeGridCell cell) //{ // //IsEditing:把编辑控件存储下来。 // var row = this.Row; // if (row != null) // { // var grid = row.TreeGrid; // if (grid != null && this.DataContext == grid.EditingItem) // { // //非回收模式下,需要把 // if (!grid.IsRecycleMode) // { // if (grid.EditingMode == TreeGridEditingMode.Row || cell.Column == grid.EditingColumn) // { // if (this._editingElements == null) // { // this._editingElements = new Dictionary<TreeGridColumn, UIElement>(); // } // this._editingElements[cell.Column] = cell.Content as UIElement; // } // } // } // } //} private void RestoreEditingContent(TreeGridCell cell, TreeGridColumn column, TreeGrid grid) { ////非回收模式下,为了返回原来的焦点,需要使用之前的编辑控件。 //if (!grid.IsRecycleMode) //{ // //如果之前已经生成了编辑控件,则使用老的控件,这样可以继续之前的编辑信息。 // if (this._editingElements != null) // { // UIElement content = null; // if (this._editingElements.TryGetValue(column, out content)) // { // cell.UpdateContent(content); // //column.PrepareElementForEdit(content as FrameworkElement, null); // //var res = content.Focus(); // //Debug.WriteLine(" content.IsVisible:" + content.IsVisible // // + " content.Focus():" + res // // + " KeyboardFocus:" + Keyboard.FocusedElement.GetType().FullName // // ); // this._editingElements.Remove(column); // } // } //} }
/// <summary> /// 修改表格的编辑状态,并让某个单元格进入编辑状态。 /// </summary> /// <param name="editingCell"></param> /// <param name="editingEventArgs">引发此操作的事件参数。可为 null。</param> private void EditCellCore(TreeGridCell editingCell, RoutedEventArgs editingEventArgs) { this._editingItem = editingCell.Row.DataContext; this._editingColumn = editingCell.Column; editingCell.SetIsEditingField(true); editingCell.FocusOnEditing(editingEventArgs); //需要把这个事件处理掉,模仿:DataGridCell.OnAnyMouseButtonDown。 if (editingEventArgs != null) { editingEventArgs.Handled = true; } }
internal TreeGridColumnCollectionChangedEventArgs(NotifyCollectionChangedAction action, TreeGridColumn newItem, TreeGridColumn oldItem, int index, int stableIndex) : base(action, newItem, oldItem, index) { this._stableIndex = stableIndex; }
/// <summary> /// How to: Sort a GridView Column When a Header Is Clicked /// http://msdn.microsoft.com/zh-cn/library/ms745786(v=VS.85).aspx /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void OnColumnHeaderClick(RoutedEventArgs e) { var header = e.OriginalSource as TreeGridColumnHeader; if (header == null || header.Column == null) return; var treeColumn = header.Column as TreeGridColumn; if (treeColumn == null) return; //如果是一些没有属性列(例如“选择”列),不需要执行排序。 var property = treeColumn.SortingProperty ?? treeColumn.PropertyName; if (property == null) return; var ascending = treeColumn.SortDirection == TreeGridColumnSortDirection.Ascending; if (this._lastSortColumn != treeColumn) { ascending = true; } else { ascending = !ascending; } var sort = new SortDescription(property, ascending ? ListSortDirection.Ascending : ListSortDirection.Descending); this.NodeSortDescriptions = new SortDescription[] { sort }; if (_lastSortColumn != null && _lastSortColumn != treeColumn) { _lastSortColumn.SortDirection = TreeGridColumnSortDirection.None; } _lastSortColumn = treeColumn; _lastSortColumn.SortDirection = ascending ? TreeGridColumnSortDirection.Ascending : TreeGridColumnSortDirection.Descending; //处理掉这个事件,包含这个 TreeGrid 的外层 TreeGrid 才不会继续排序。 e.Handled = true; }
internal TreeGridColumnCollectionChangedEventArgs(NotifyCollectionChangedAction action, TreeGridColumn changedItem, int index, int oldIndex, int stableIndex) : base(action, changedItem, index, oldIndex) { this._stableIndex = stableIndex; }
internal TreeGridColumnCollectionChangedEventArgs(TreeGridColumn column, string propertyName) : base(NotifyCollectionChangedAction.Reset) { this._column = column; this._propertyName = propertyName; }
/// <summary> /// 在编辑控件按 Tab 切换到下一列 /// </summary> /// <param name="cell"></param> /// <param name="moveNext">是向后编辑还是向前编辑。</param> /// <param name="e"></param> /// <param name="firstStarted"></param> internal void EditNextColumnOnTabKey(TreeGridCell cell, bool moveNext, KeyEventArgs e, TreeGridColumn firstStarted) { var grid = this.TreeGrid; var columns = grid.Columns; var index = columns.IndexOf(this); index += moveNext ? 1 : -1; //循环:如果是最后一个,则使用第一个;如果是第一个,则使用最后一个。 if (index >= columns.Count) { index = 0; } else if (index < 0) { index = columns.Count - 1; } //尝试编辑 var row = cell.Row; if (row != null) { var nextColumn = columns[index] as TreeGridColumn; //如果要编辑的单元格和起始单元格是同一个格子,则已经循环了一次,不需要继续了。 if (nextColumn == firstStarted) return; grid.BringColumnIntoView(index); var nextCell = row.FindCell(nextColumn); if (nextCell != null) { bool success = false; if (grid.EditingMode == TreeGridEditingMode.Cell) { success = grid.TryEditCell(nextCell, e); } else { //行模式下,只是把焦点移到下一个单元格即可。 if (nextCell.IsEditing) { nextCell.FocusOnEditing(e); success = true; } } if (success) { e.Handled = true; return; } //如果 nextCell 编辑失败,并且不是循环第二次,则继续编辑下一个。 nextColumn.EditNextColumnOnTabKey(nextCell, moveNext, e, firstStarted); } } }
/// <summary> /// 为指定列生成 header 并添加到 InternalChildren 的索引 index 处。 /// </summary> /// <param name="column"></param> /// <param name="index"></param> /// <returns></returns> private TreeGridColumnHeader CreateAndInsertHeader(TreeGridColumn column, int index) { object header = column.Header; var gridViewColumnHeader = header as TreeGridColumnHeader; if (header != null) { var dependencyObject = header as DependencyObject; if (dependencyObject != null) { var visual = dependencyObject as Visual; if (visual != null) { var visual2 = VisualTreeHelper.GetParent(visual) as Visual; if (visual2 != null) { if (gridViewColumnHeader != null) { var gridViewHeaderRowPresenter = visual2 as TreeGridHeaderRowPresenter; if (gridViewHeaderRowPresenter != null) { MSInternal.RemoveNoVerify(gridViewHeaderRowPresenter.UIChildren, gridViewColumnHeader); } } else { var gridViewColumnHeader2 = visual2 as TreeGridColumnHeader; if (gridViewColumnHeader2 != null) { gridViewColumnHeader2.ClearValue(ContentControl.ContentProperty); } } } } var parent = LogicalTreeHelper.GetParent(dependencyObject); if (parent != null) { MSInternal.RemoveLogicalChild(parent, header); } } } if (gridViewColumnHeader == null) { gridViewColumnHeader = new TreeGridColumnHeader(); gridViewColumnHeader.IsInternalGenerated = true; } gridViewColumnHeader.SetValue(TreeGridColumnHeader.ColumnPropertyKey, column); this.HookupItemsControlKeyboardEvent(gridViewColumnHeader); base.UIChildren.Insert(index, gridViewColumnHeader); this.UpdateHeader(gridViewColumnHeader); this._gvHeadersValid = false; return gridViewColumnHeader; }
private TreeGridColumnHeader FindHeaderByColumn(TreeGridColumn column) { var columns = base.Columns; UIElementCollection internalChildren = base.UIChildren; if (internalChildren.Count > columns.Count) { int num = columns.IndexOf(column); if (num != -1) { int visualIndex = this.GetVisualIndex(num); TreeGridColumnHeader gridViewColumnHeader = internalChildren[visualIndex] as TreeGridColumnHeader; if (gridViewColumnHeader.Column == column) { return gridViewColumnHeader; } for (int i = 1; i < internalChildren.Count; i++) { gridViewColumnHeader = (internalChildren[i] as TreeGridColumnHeader); if (gridViewColumnHeader != null && gridViewColumnHeader.Column == column) { return gridViewColumnHeader; } } } } return null; }
/// <summary> /// 尝试找到指定对象的指定单元格。 /// 如果该行该列正处于虚拟化中,则返回 null。 /// </summary> /// <param name="item"></param> /// <param name="column"></param> /// <returns></returns> public TreeGridCell FindCell(object item, TreeGridColumn column) { TreeGridCell cell = null; var row = this.FindRow(item); if (row != null) { cell = row.FindCell(column); } return cell; }
/// <summary> /// 把指定的列滚动到视区中。 /// </summary> /// <param name="column"></param> public void BringColumnIntoView(TreeGridColumn column) { var columnIndex = this.Columns.IndexOf(column); this.BringColumnIntoView(columnIndex); }
/// <summary> /// 当某个 TreeGridColumn 的属性变更时,把这个变更同步到相应的单元格上。 /// </summary> /// <param name="column"></param> /// <param name="propertyName"></param> private void OnColumnPropertyChanged(TreeGridColumn column, string propertyName) { if (TreeGridColumn.c_ActualWidthName == propertyName) { return; } //列宽变化时,重新测量 if (TreeGridColumn.WidthProperty.Name == propertyName) { base.InvalidateMeasure(); return; } int actualIndex = column.StableIndex; if (actualIndex >= 0 && actualIndex < base.InternalChildren.Count) { var cell = base.InternalChildren[actualIndex] as TreeGridCell; if (cell != null) { if (TreeGridColumn.BindingProperty.Name == propertyName) { var textBlock = cell.Content as TextBlock; if (textBlock != null) { var displayMemberBinding = column.Binding; if (displayMemberBinding != null) { textBlock.SetBinding(TextBlock.TextProperty, displayMemberBinding); } } } else if (TreeGridColumn.CellStyleProperty.Name == propertyName) { cell.Style = column.CellStyle; } else if (TreeGridColumn.CellContentTemplateProperty.Name == propertyName) { cell.ContentTemplate = column.GetDisplayCellTemplate(); } else if (TreeGridColumn.CellContentTemplateSelectorProperty.Name == propertyName) { cell.ContentTemplateSelector = column.CellContentTemplateSelector; } } } }
/// <summary> /// 在编辑控件按 Tab 切换到下一列 /// </summary> /// <param name="cell"></param> /// <param name="moveNext">是向后编辑还是向前编辑。</param> /// <param name="e"></param> /// <param name="firstStarted"></param> internal void EditNextColumnOnTabKey(TreeGridCell cell, bool moveNext, KeyEventArgs e, TreeGridColumn firstStarted) { var grid = this.TreeGrid; var columns = grid.Columns; var index = columns.IndexOf(this); index += moveNext ? 1 : -1; //循环:如果是最后一个,则使用第一个;如果是第一个,则使用最后一个。 if (index >= columns.Count) { index = 0; } else if (index < 0) { index = columns.Count - 1; } //尝试编辑 var row = cell.Row; if (row != null) { var nextColumn = columns[index] as TreeGridColumn; //如果要编辑的单元格和起始单元格是同一个格子,则已经循环了一次,不需要继续了。 if (nextColumn == firstStarted) { return; } grid.BringColumnIntoView(index); var nextCell = row.FindCell(nextColumn); if (nextCell != null) { bool success = false; if (grid.EditingMode == TreeGridEditingMode.Cell) { success = grid.TryEditCell(nextCell, e); } else { //行模式下,只是把焦点移到下一个单元格即可。 if (nextCell.IsEditing) { nextCell.FocusOnEditing(e); success = true; } } if (success) { e.Handled = true; return; } //如果 nextCell 编辑失败,并且不是循环第二次,则继续编辑下一个。 nextColumn.EditNextColumnOnTabKey(nextCell, moveNext, e, firstStarted); } } }
private void PrepareCell(TreeGridCell cell, TreeGridColumn column) { cell.Column = column; if (column.CellStyle != null) { cell.Style = column.CellStyle; } cell.UpdateContent(false); //IsEditing var row = this.Row; if (row != null) { var grid = row.TreeGrid; //当前行是表格中正在编辑的行 if (grid != null && this.DataContext == grid.EditingItem) { //整行编辑、或者正在编辑该单元格 if (grid.EditingMode == TreeGridEditingMode.Row || column == grid.EditingColumn) { if (cell.Column.CanEdit(cell.DataContext)) { cell.SetIsEditingField(true); //this.RestoreEditingContent(cell, column, grid); } } } } //Automation var headerLabel = column.HeaderLabel; if (!string.IsNullOrEmpty(headerLabel)) { AutomationProperties.SetName(cell, headerLabel); } }
/// <summary> /// 退出当前单元格编辑状态 /// </summary> private void ExitCellEditing() { if (this._editingItem != null && this._editingColumn != null) { var editingCell = this.FindEditingCell(); if (editingCell != null) editingCell.SetIsEditingField(false); this._editingItem = null; this._editingColumn = null; } }
internal TreeGridColumnCollectionChangedEventArgs(NotifyCollectionChangedAction action, TreeGridColumn[] clearedColumns) : base(action) { this._clearedColumns = Array.AsReadOnly<TreeGridColumn>(clearedColumns); }
/// <summary> /// 当某个 TreeGridColumn 的属性变更时,会发生此事件。 /// </summary> /// <param name="column"></param> /// <param name="propertyName"></param> internal virtual void OnColumnPropertyChanged(TreeGridColumn column, string propertyName) { if (column.StableIndex >= 0) { if (TreeGridColumn.WidthProperty.Name == propertyName || TreeGridColumn.c_ActualWidthName == propertyName) { base.InvalidateMeasure(); } } }
/// <summary> /// 在列的属性变化时,尝试重新绘制界面 /// </summary> /// <param name="column"></param> /// <param name="propertyName"></param> internal override void OnColumnPropertyChanged(TreeGridColumn column, string propertyName) { base.OnColumnPropertyChanged(column, propertyName); if (column.StableIndex >= 0) { var header = this.FindHeaderByColumn(column); if (header != null) { if (TreeGridColumn.HeaderProperty.Name == propertyName) { if (!header.IsInternalGenerated || column.Header is TreeGridColumnHeader) { int index = base.UIChildren.IndexOf(header); this.RemoveHeader(header, -1); this.CreateAndInsertHeader(column, index); this.BuildHeaderLinks(); return; } this.UpdateHeaderContent(header); } else { var columnDPFromName = TreeGridHeaderRowPresenter.GetColumnDPFromName(propertyName); if (columnDPFromName != null) { this.UpdateHeaderProperty(header, columnDPFromName); } } } } }