Code:
/ 4.0 / 4.0 / DEVDIV_TFS / Dev10 / Releases / RTMRel / wpf / src / Framework / System / Windows / Controls / DataGridComboBoxColumn.cs / 1305600 / DataGridComboBoxColumn.cs
//---------------------------------------------------------------------------- // // Copyright (C) Microsoft Corporation. All rights reserved. // //--------------------------------------------------------------------------- using System; using System.Collections; using System.ComponentModel; using System.Diagnostics; using System.Windows; using System.Windows.Data; using System.Windows.Input; namespace System.Windows.Controls { ////// A column that displays a drop-down list while in edit mode. /// public class DataGridComboBoxColumn : DataGridColumn { #region Constructors static DataGridComboBoxColumn() { SortMemberPathProperty.OverrideMetadata(typeof(DataGridComboBoxColumn), new FrameworkPropertyMetadata(null, OnCoerceSortMemberPath)); } #endregion #region Helper Type for Styling internal class TextBlockComboBox : ComboBox { static TextBlockComboBox() { DefaultStyleKeyProperty.OverrideMetadata(typeof(TextBlockComboBox), new FrameworkPropertyMetadata(DataGridComboBoxColumn.TextBlockComboBoxStyleKey)); KeyboardNavigation.IsTabStopProperty.OverrideMetadata(typeof(TextBlockComboBox), new FrameworkPropertyMetadata(false)); } } ////// Style key for TextBlockComboBox /// public static ComponentResourceKey TextBlockComboBoxStyleKey { get { return SystemResourceKey.DataGridComboBoxColumnTextBlockComboBoxStyleKey; } } #endregion #region Binding private static object OnCoerceSortMemberPath(DependencyObject d, object baseValue) { var column = (DataGridComboBoxColumn)d; var sortMemberPath = (string)baseValue; if (string.IsNullOrEmpty(sortMemberPath)) { var bindingSortMemberPath = DataGridHelper.GetPathFromBinding(column.EffectiveBinding as Binding); if (!string.IsNullOrEmpty(bindingSortMemberPath)) { sortMemberPath = bindingSortMemberPath; } } return sortMemberPath; } ////// Chooses either SelectedItemBinding, TextBinding, SelectedValueBinding or based which are set. /// private BindingBase EffectiveBinding { get { if (SelectedItemBinding != null) { return SelectedItemBinding; } else if (SelectedValueBinding != null) { return SelectedValueBinding; } else { return TextBinding; } } } ////// The binding that will be applied to the SelectedValue property of the ComboBox. This works in conjunction with SelectedValuePath /// ////// This isn't a DP because if it were getting the value would evaluate the binding. /// public virtual BindingBase SelectedValueBinding { get { return _selectedValueBinding; } set { if (_selectedValueBinding != value) { BindingBase oldBinding = _selectedValueBinding; _selectedValueBinding = value; CoerceValue(IsReadOnlyProperty); CoerceValue(SortMemberPathProperty); OnSelectedValueBindingChanged(oldBinding, _selectedValueBinding); } } } protected override bool OnCoerceIsReadOnly(bool baseValue) { if (DataGridHelper.IsOneWay(EffectiveBinding)) { return true; } // only call the base if we dont want to force IsReadOnly true return base.OnCoerceIsReadOnly(baseValue); } ////// The binding that will be applied to the SelectedItem property of the ComboBoxValue. /// ////// This isn't a DP because if it were getting the value would evaluate the binding. /// public virtual BindingBase SelectedItemBinding { get { return _selectedItemBinding; } set { if (_selectedItemBinding != value) { BindingBase oldBinding = _selectedItemBinding; _selectedItemBinding = value; CoerceValue(IsReadOnlyProperty); CoerceValue(SortMemberPathProperty); OnSelectedItemBindingChanged(oldBinding, _selectedItemBinding); } } } ////// The binding that will be applied to the Text property of the ComboBoxValue. /// ////// This isn't a DP because if it were getting the value would evaluate the binding. /// public virtual BindingBase TextBinding { get { return _textBinding; } set { if (_textBinding != value) { BindingBase oldBinding = _textBinding; _textBinding = value; CoerceValue(IsReadOnlyProperty); CoerceValue(SortMemberPathProperty); OnTextBindingChanged(oldBinding, _textBinding); } } } ////// Called when SelectedValueBinding changes. /// /// The old binding. /// The new binding. protected virtual void OnSelectedValueBindingChanged(BindingBase oldBinding, BindingBase newBinding) { NotifyPropertyChanged("SelectedValueBinding"); } ////// Called when SelectedItemBinding changes. /// /// The old binding. /// The new binding. protected virtual void OnSelectedItemBindingChanged(BindingBase oldBinding, BindingBase newBinding) { NotifyPropertyChanged("SelectedItemBinding"); } ////// Called when TextBinding changes. /// /// The old binding. /// The new binding. protected virtual void OnTextBindingChanged(BindingBase oldBinding, BindingBase newBinding) { NotifyPropertyChanged("TextBinding"); } #endregion #region Styling ////// The default value of the ElementStyle property. /// This value can be used as the BasedOn for new styles. /// public static Style DefaultElementStyle { get { if (_defaultElementStyle == null) { Style style = new Style(typeof(ComboBox)); // Set IsSynchronizedWithCurrentItem to false by default style.Setters.Add(new Setter(ComboBox.IsSynchronizedWithCurrentItemProperty, false)); style.Seal(); _defaultElementStyle = style; } return _defaultElementStyle; } } ////// The default value of the EditingElementStyle property. /// This value can be used as the BasedOn for new styles. /// public static Style DefaultEditingElementStyle { get { // return the same as that of DefaultElementStyle return DefaultElementStyle; } } ////// A style that is applied to the generated element when not editing. /// The TargetType of the style depends on the derived column class. /// public Style ElementStyle { get { return (Style)GetValue(ElementStyleProperty); } set { SetValue(ElementStyleProperty, value); } } ////// The DependencyProperty for the ElementStyle property. /// public static readonly DependencyProperty ElementStyleProperty = DataGridBoundColumn.ElementStyleProperty.AddOwner(typeof(DataGridComboBoxColumn), new FrameworkPropertyMetadata(DefaultElementStyle)); ////// A style that is applied to the generated element when editing. /// The TargetType of the style depends on the derived column class. /// public Style EditingElementStyle { get { return (Style)GetValue(EditingElementStyleProperty); } set { SetValue(EditingElementStyleProperty, value); } } ////// The DependencyProperty for the EditingElementStyle property. /// public static readonly DependencyProperty EditingElementStyleProperty = DataGridBoundColumn.EditingElementStyleProperty.AddOwner(typeof(DataGridComboBoxColumn), new FrameworkPropertyMetadata(DefaultEditingElementStyle)); ////// Assigns the ElementStyle to the desired property on the given element. /// private void ApplyStyle(bool isEditing, bool defaultToElementStyle, FrameworkElement element) { Style style = PickStyle(isEditing, defaultToElementStyle); if (style != null) { element.Style = style; } } ////// Assigns the ElementStyle to the desired property on the given element. /// internal void ApplyStyle(bool isEditing, bool defaultToElementStyle, FrameworkContentElement element) { Style style = PickStyle(isEditing, defaultToElementStyle); if (style != null) { element.Style = style; } } private Style PickStyle(bool isEditing, bool defaultToElementStyle) { Style style = isEditing ? EditingElementStyle : ElementStyle; if (isEditing && defaultToElementStyle && (style == null)) { style = ElementStyle; } return style; } ////// Assigns the Binding to the desired property on the target object. /// private static void ApplyBinding(BindingBase binding, DependencyObject target, DependencyProperty property) { if (binding != null) { BindingOperations.SetBinding(target, property, binding); } else { BindingOperations.ClearBinding(target, property); } } #endregion #region Clipboard Copy/Paste ////// If base ClipboardContentBinding is not set we use Binding. /// public override BindingBase ClipboardContentBinding { get { return base.ClipboardContentBinding ?? EffectiveBinding; } set { base.ClipboardContentBinding = value; } } #endregion #region ComboBox Column Properties ////// The ComboBox will attach to this ItemsSource. /// public IEnumerable ItemsSource { get { return (IEnumerable)GetValue(ItemsSourceProperty); } set { SetValue(ItemsSourceProperty, value); } } ////// The DependencyProperty for ItemsSource. /// public static readonly DependencyProperty ItemsSourceProperty = ComboBox.ItemsSourceProperty.AddOwner(typeof(DataGridComboBoxColumn), new FrameworkPropertyMetadata(null, DataGridColumn.NotifyPropertyChangeForRefreshContent)); ////// DisplayMemberPath is a simple way to define a default template /// that describes how to convert Items into UI elements by using /// the specified path. /// public string DisplayMemberPath { get { return (string)GetValue(DisplayMemberPathProperty); } set { SetValue(DisplayMemberPathProperty, value); } } ////// The DependencyProperty for the DisplayMemberPath property. /// public static readonly DependencyProperty DisplayMemberPathProperty = ComboBox.DisplayMemberPathProperty.AddOwner(typeof(DataGridComboBoxColumn), new FrameworkPropertyMetadata(string.Empty, DataGridColumn.NotifyPropertyChangeForRefreshContent)); ////// The path used to retrieve the SelectedValue from the SelectedItem /// public string SelectedValuePath { get { return (string)GetValue(SelectedValuePathProperty); } set { SetValue(SelectedValuePathProperty, value); } } ////// SelectedValuePath DependencyProperty /// public static readonly DependencyProperty SelectedValuePathProperty = ComboBox.SelectedValuePathProperty.AddOwner(typeof(DataGridComboBoxColumn), new FrameworkPropertyMetadata(string.Empty, DataGridColumn.NotifyPropertyChangeForRefreshContent)); #endregion #region Property Changed Handler protected internal override void RefreshCellContent(FrameworkElement element, string propertyName) { DataGridCell cell = element as DataGridCell; if (cell != null) { bool isCellEditing = cell.IsEditing; if ((string.Compare(propertyName, "ElementStyle", StringComparison.Ordinal) == 0 && !isCellEditing) || (string.Compare(propertyName, "EditingElementStyle", StringComparison.Ordinal) == 0 && isCellEditing)) { cell.BuildVisualTree(); } else { ComboBox comboBox = cell.Content as ComboBox; switch (propertyName) { case "SelectedItemBinding": ApplyBinding(SelectedItemBinding, comboBox, ComboBox.SelectedItemProperty); break; case "SelectedValueBinding": ApplyBinding(SelectedValueBinding, comboBox, ComboBox.SelectedValueProperty); break; case "TextBinding": ApplyBinding(TextBinding, comboBox, ComboBox.TextProperty); break; case "SelectedValuePath": DataGridHelper.SyncColumnProperty(this, comboBox, ComboBox.SelectedValuePathProperty, SelectedValuePathProperty); break; case "DisplayMemberPath": DataGridHelper.SyncColumnProperty(this, comboBox, ComboBox.DisplayMemberPathProperty, DisplayMemberPathProperty); break; case "ItemsSource": DataGridHelper.SyncColumnProperty(this, comboBox, ComboBox.ItemsSourceProperty, ItemsSourceProperty); break; default: base.RefreshCellContent(element, propertyName); break; } } } else { base.RefreshCellContent(element, propertyName); } } #endregion #region BindingTarget Helpers ////// Helper method which returns selection value from /// combobox based on which Binding's were set. /// /// ///private object GetComboBoxSelectionValue(ComboBox comboBox) { if (SelectedItemBinding != null) { return comboBox.SelectedItem; } else if (SelectedValueBinding != null) { return comboBox.SelectedValue; } else { return comboBox.Text; } } #endregion #region Element Generation /// /// Creates the visual tree for text based cells. /// protected override FrameworkElement GenerateElement(DataGridCell cell, object dataItem) { TextBlockComboBox comboBox = new TextBlockComboBox(); ApplyStyle(/* isEditing = */ false, /* defaultToElementStyle = */ false, comboBox); ApplyColumnProperties(comboBox); return comboBox; } ////// Creates the visual tree for text based cells. /// protected override FrameworkElement GenerateEditingElement(DataGridCell cell, object dataItem) { ComboBox comboBox = new ComboBox(); ApplyStyle(/* isEditing = */ true, /* defaultToElementStyle = */ false, comboBox); ApplyColumnProperties(comboBox); return comboBox; } private void ApplyColumnProperties(ComboBox comboBox) { ApplyBinding(SelectedItemBinding, comboBox, ComboBox.SelectedItemProperty); ApplyBinding(SelectedValueBinding, comboBox, ComboBox.SelectedValueProperty); ApplyBinding(TextBinding, comboBox, ComboBox.TextProperty); DataGridHelper.SyncColumnProperty(this, comboBox, ComboBox.SelectedValuePathProperty, SelectedValuePathProperty); DataGridHelper.SyncColumnProperty(this, comboBox, ComboBox.DisplayMemberPathProperty, DisplayMemberPathProperty); DataGridHelper.SyncColumnProperty(this, comboBox, ComboBox.ItemsSourceProperty, ItemsSourceProperty); } #endregion #region Editing ////// Called when a cell has just switched to edit mode. /// /// A reference to element returned by GenerateEditingElement. /// The event args of the input event that caused the cell to go into edit mode. May be null. ///The unedited value of the cell. protected override object PrepareCellForEdit(FrameworkElement editingElement, RoutedEventArgs editingEventArgs) { ComboBox comboBox = editingElement as ComboBox; if (comboBox != null) { comboBox.Focus(); object originalValue = GetComboBoxSelectionValue(comboBox); if (IsComboBoxOpeningInputEvent(editingEventArgs)) { comboBox.IsDropDownOpen = true; } return originalValue; } return null; } internal override void OnInput(InputEventArgs e) { if (IsComboBoxOpeningInputEvent(e)) { BeginEdit(e); } } private static bool IsComboBoxOpeningInputEvent(RoutedEventArgs e) { KeyEventArgs keyArgs = e as KeyEventArgs; if ((keyArgs != null) && ((keyArgs.KeyStates & KeyStates.Down) == KeyStates.Down)) { bool isAltDown = (keyArgs.KeyboardDevice.Modifiers & ModifierKeys.Alt) == ModifierKeys.Alt; // We want to handle the ALT key. Get the real key if it is Key.System. Key key = keyArgs.Key; if (key == Key.System) { key = keyArgs.SystemKey; } // F4 alone or ALT+Up or ALT+Down will open the drop-down return ((key == Key.F4) && !isAltDown) || (((key == Key.Up) || (key == Key.Down)) && isAltDown); } return false; } #endregion #region Data private static Style _defaultElementStyle; private BindingBase _selectedValueBinding; private BindingBase _selectedItemBinding; private BindingBase _textBinding; #endregion } } // File provided for Reference Use Only by Microsoft Corporation (c) 2007. // Copyright (c) Microsoft Corporation. All rights reserved. //---------------------------------------------------------------------------- // // Copyright (C) Microsoft Corporation. All rights reserved. // //--------------------------------------------------------------------------- using System; using System.Collections; using System.ComponentModel; using System.Diagnostics; using System.Windows; using System.Windows.Data; using System.Windows.Input; namespace System.Windows.Controls { ////// A column that displays a drop-down list while in edit mode. /// public class DataGridComboBoxColumn : DataGridColumn { #region Constructors static DataGridComboBoxColumn() { SortMemberPathProperty.OverrideMetadata(typeof(DataGridComboBoxColumn), new FrameworkPropertyMetadata(null, OnCoerceSortMemberPath)); } #endregion #region Helper Type for Styling internal class TextBlockComboBox : ComboBox { static TextBlockComboBox() { DefaultStyleKeyProperty.OverrideMetadata(typeof(TextBlockComboBox), new FrameworkPropertyMetadata(DataGridComboBoxColumn.TextBlockComboBoxStyleKey)); KeyboardNavigation.IsTabStopProperty.OverrideMetadata(typeof(TextBlockComboBox), new FrameworkPropertyMetadata(false)); } } ////// Style key for TextBlockComboBox /// public static ComponentResourceKey TextBlockComboBoxStyleKey { get { return SystemResourceKey.DataGridComboBoxColumnTextBlockComboBoxStyleKey; } } #endregion #region Binding private static object OnCoerceSortMemberPath(DependencyObject d, object baseValue) { var column = (DataGridComboBoxColumn)d; var sortMemberPath = (string)baseValue; if (string.IsNullOrEmpty(sortMemberPath)) { var bindingSortMemberPath = DataGridHelper.GetPathFromBinding(column.EffectiveBinding as Binding); if (!string.IsNullOrEmpty(bindingSortMemberPath)) { sortMemberPath = bindingSortMemberPath; } } return sortMemberPath; } ////// Chooses either SelectedItemBinding, TextBinding, SelectedValueBinding or based which are set. /// private BindingBase EffectiveBinding { get { if (SelectedItemBinding != null) { return SelectedItemBinding; } else if (SelectedValueBinding != null) { return SelectedValueBinding; } else { return TextBinding; } } } ////// The binding that will be applied to the SelectedValue property of the ComboBox. This works in conjunction with SelectedValuePath /// ////// This isn't a DP because if it were getting the value would evaluate the binding. /// public virtual BindingBase SelectedValueBinding { get { return _selectedValueBinding; } set { if (_selectedValueBinding != value) { BindingBase oldBinding = _selectedValueBinding; _selectedValueBinding = value; CoerceValue(IsReadOnlyProperty); CoerceValue(SortMemberPathProperty); OnSelectedValueBindingChanged(oldBinding, _selectedValueBinding); } } } protected override bool OnCoerceIsReadOnly(bool baseValue) { if (DataGridHelper.IsOneWay(EffectiveBinding)) { return true; } // only call the base if we dont want to force IsReadOnly true return base.OnCoerceIsReadOnly(baseValue); } ////// The binding that will be applied to the SelectedItem property of the ComboBoxValue. /// ////// This isn't a DP because if it were getting the value would evaluate the binding. /// public virtual BindingBase SelectedItemBinding { get { return _selectedItemBinding; } set { if (_selectedItemBinding != value) { BindingBase oldBinding = _selectedItemBinding; _selectedItemBinding = value; CoerceValue(IsReadOnlyProperty); CoerceValue(SortMemberPathProperty); OnSelectedItemBindingChanged(oldBinding, _selectedItemBinding); } } } ////// The binding that will be applied to the Text property of the ComboBoxValue. /// ////// This isn't a DP because if it were getting the value would evaluate the binding. /// public virtual BindingBase TextBinding { get { return _textBinding; } set { if (_textBinding != value) { BindingBase oldBinding = _textBinding; _textBinding = value; CoerceValue(IsReadOnlyProperty); CoerceValue(SortMemberPathProperty); OnTextBindingChanged(oldBinding, _textBinding); } } } ////// Called when SelectedValueBinding changes. /// /// The old binding. /// The new binding. protected virtual void OnSelectedValueBindingChanged(BindingBase oldBinding, BindingBase newBinding) { NotifyPropertyChanged("SelectedValueBinding"); } ////// Called when SelectedItemBinding changes. /// /// The old binding. /// The new binding. protected virtual void OnSelectedItemBindingChanged(BindingBase oldBinding, BindingBase newBinding) { NotifyPropertyChanged("SelectedItemBinding"); } ////// Called when TextBinding changes. /// /// The old binding. /// The new binding. protected virtual void OnTextBindingChanged(BindingBase oldBinding, BindingBase newBinding) { NotifyPropertyChanged("TextBinding"); } #endregion #region Styling ////// The default value of the ElementStyle property. /// This value can be used as the BasedOn for new styles. /// public static Style DefaultElementStyle { get { if (_defaultElementStyle == null) { Style style = new Style(typeof(ComboBox)); // Set IsSynchronizedWithCurrentItem to false by default style.Setters.Add(new Setter(ComboBox.IsSynchronizedWithCurrentItemProperty, false)); style.Seal(); _defaultElementStyle = style; } return _defaultElementStyle; } } ////// The default value of the EditingElementStyle property. /// This value can be used as the BasedOn for new styles. /// public static Style DefaultEditingElementStyle { get { // return the same as that of DefaultElementStyle return DefaultElementStyle; } } ////// A style that is applied to the generated element when not editing. /// The TargetType of the style depends on the derived column class. /// public Style ElementStyle { get { return (Style)GetValue(ElementStyleProperty); } set { SetValue(ElementStyleProperty, value); } } ////// The DependencyProperty for the ElementStyle property. /// public static readonly DependencyProperty ElementStyleProperty = DataGridBoundColumn.ElementStyleProperty.AddOwner(typeof(DataGridComboBoxColumn), new FrameworkPropertyMetadata(DefaultElementStyle)); ////// A style that is applied to the generated element when editing. /// The TargetType of the style depends on the derived column class. /// public Style EditingElementStyle { get { return (Style)GetValue(EditingElementStyleProperty); } set { SetValue(EditingElementStyleProperty, value); } } ////// The DependencyProperty for the EditingElementStyle property. /// public static readonly DependencyProperty EditingElementStyleProperty = DataGridBoundColumn.EditingElementStyleProperty.AddOwner(typeof(DataGridComboBoxColumn), new FrameworkPropertyMetadata(DefaultEditingElementStyle)); ////// Assigns the ElementStyle to the desired property on the given element. /// private void ApplyStyle(bool isEditing, bool defaultToElementStyle, FrameworkElement element) { Style style = PickStyle(isEditing, defaultToElementStyle); if (style != null) { element.Style = style; } } ////// Assigns the ElementStyle to the desired property on the given element. /// internal void ApplyStyle(bool isEditing, bool defaultToElementStyle, FrameworkContentElement element) { Style style = PickStyle(isEditing, defaultToElementStyle); if (style != null) { element.Style = style; } } private Style PickStyle(bool isEditing, bool defaultToElementStyle) { Style style = isEditing ? EditingElementStyle : ElementStyle; if (isEditing && defaultToElementStyle && (style == null)) { style = ElementStyle; } return style; } ////// Assigns the Binding to the desired property on the target object. /// private static void ApplyBinding(BindingBase binding, DependencyObject target, DependencyProperty property) { if (binding != null) { BindingOperations.SetBinding(target, property, binding); } else { BindingOperations.ClearBinding(target, property); } } #endregion #region Clipboard Copy/Paste ////// If base ClipboardContentBinding is not set we use Binding. /// public override BindingBase ClipboardContentBinding { get { return base.ClipboardContentBinding ?? EffectiveBinding; } set { base.ClipboardContentBinding = value; } } #endregion #region ComboBox Column Properties ////// The ComboBox will attach to this ItemsSource. /// public IEnumerable ItemsSource { get { return (IEnumerable)GetValue(ItemsSourceProperty); } set { SetValue(ItemsSourceProperty, value); } } ////// The DependencyProperty for ItemsSource. /// public static readonly DependencyProperty ItemsSourceProperty = ComboBox.ItemsSourceProperty.AddOwner(typeof(DataGridComboBoxColumn), new FrameworkPropertyMetadata(null, DataGridColumn.NotifyPropertyChangeForRefreshContent)); ////// DisplayMemberPath is a simple way to define a default template /// that describes how to convert Items into UI elements by using /// the specified path. /// public string DisplayMemberPath { get { return (string)GetValue(DisplayMemberPathProperty); } set { SetValue(DisplayMemberPathProperty, value); } } ////// The DependencyProperty for the DisplayMemberPath property. /// public static readonly DependencyProperty DisplayMemberPathProperty = ComboBox.DisplayMemberPathProperty.AddOwner(typeof(DataGridComboBoxColumn), new FrameworkPropertyMetadata(string.Empty, DataGridColumn.NotifyPropertyChangeForRefreshContent)); ////// The path used to retrieve the SelectedValue from the SelectedItem /// public string SelectedValuePath { get { return (string)GetValue(SelectedValuePathProperty); } set { SetValue(SelectedValuePathProperty, value); } } ////// SelectedValuePath DependencyProperty /// public static readonly DependencyProperty SelectedValuePathProperty = ComboBox.SelectedValuePathProperty.AddOwner(typeof(DataGridComboBoxColumn), new FrameworkPropertyMetadata(string.Empty, DataGridColumn.NotifyPropertyChangeForRefreshContent)); #endregion #region Property Changed Handler protected internal override void RefreshCellContent(FrameworkElement element, string propertyName) { DataGridCell cell = element as DataGridCell; if (cell != null) { bool isCellEditing = cell.IsEditing; if ((string.Compare(propertyName, "ElementStyle", StringComparison.Ordinal) == 0 && !isCellEditing) || (string.Compare(propertyName, "EditingElementStyle", StringComparison.Ordinal) == 0 && isCellEditing)) { cell.BuildVisualTree(); } else { ComboBox comboBox = cell.Content as ComboBox; switch (propertyName) { case "SelectedItemBinding": ApplyBinding(SelectedItemBinding, comboBox, ComboBox.SelectedItemProperty); break; case "SelectedValueBinding": ApplyBinding(SelectedValueBinding, comboBox, ComboBox.SelectedValueProperty); break; case "TextBinding": ApplyBinding(TextBinding, comboBox, ComboBox.TextProperty); break; case "SelectedValuePath": DataGridHelper.SyncColumnProperty(this, comboBox, ComboBox.SelectedValuePathProperty, SelectedValuePathProperty); break; case "DisplayMemberPath": DataGridHelper.SyncColumnProperty(this, comboBox, ComboBox.DisplayMemberPathProperty, DisplayMemberPathProperty); break; case "ItemsSource": DataGridHelper.SyncColumnProperty(this, comboBox, ComboBox.ItemsSourceProperty, ItemsSourceProperty); break; default: base.RefreshCellContent(element, propertyName); break; } } } else { base.RefreshCellContent(element, propertyName); } } #endregion #region BindingTarget Helpers ////// Helper method which returns selection value from /// combobox based on which Binding's were set. /// /// ///private object GetComboBoxSelectionValue(ComboBox comboBox) { if (SelectedItemBinding != null) { return comboBox.SelectedItem; } else if (SelectedValueBinding != null) { return comboBox.SelectedValue; } else { return comboBox.Text; } } #endregion #region Element Generation /// /// Creates the visual tree for text based cells. /// protected override FrameworkElement GenerateElement(DataGridCell cell, object dataItem) { TextBlockComboBox comboBox = new TextBlockComboBox(); ApplyStyle(/* isEditing = */ false, /* defaultToElementStyle = */ false, comboBox); ApplyColumnProperties(comboBox); return comboBox; } ////// Creates the visual tree for text based cells. /// protected override FrameworkElement GenerateEditingElement(DataGridCell cell, object dataItem) { ComboBox comboBox = new ComboBox(); ApplyStyle(/* isEditing = */ true, /* defaultToElementStyle = */ false, comboBox); ApplyColumnProperties(comboBox); return comboBox; } private void ApplyColumnProperties(ComboBox comboBox) { ApplyBinding(SelectedItemBinding, comboBox, ComboBox.SelectedItemProperty); ApplyBinding(SelectedValueBinding, comboBox, ComboBox.SelectedValueProperty); ApplyBinding(TextBinding, comboBox, ComboBox.TextProperty); DataGridHelper.SyncColumnProperty(this, comboBox, ComboBox.SelectedValuePathProperty, SelectedValuePathProperty); DataGridHelper.SyncColumnProperty(this, comboBox, ComboBox.DisplayMemberPathProperty, DisplayMemberPathProperty); DataGridHelper.SyncColumnProperty(this, comboBox, ComboBox.ItemsSourceProperty, ItemsSourceProperty); } #endregion #region Editing ////// Called when a cell has just switched to edit mode. /// /// A reference to element returned by GenerateEditingElement. /// The event args of the input event that caused the cell to go into edit mode. May be null. ///The unedited value of the cell. protected override object PrepareCellForEdit(FrameworkElement editingElement, RoutedEventArgs editingEventArgs) { ComboBox comboBox = editingElement as ComboBox; if (comboBox != null) { comboBox.Focus(); object originalValue = GetComboBoxSelectionValue(comboBox); if (IsComboBoxOpeningInputEvent(editingEventArgs)) { comboBox.IsDropDownOpen = true; } return originalValue; } return null; } internal override void OnInput(InputEventArgs e) { if (IsComboBoxOpeningInputEvent(e)) { BeginEdit(e); } } private static bool IsComboBoxOpeningInputEvent(RoutedEventArgs e) { KeyEventArgs keyArgs = e as KeyEventArgs; if ((keyArgs != null) && ((keyArgs.KeyStates & KeyStates.Down) == KeyStates.Down)) { bool isAltDown = (keyArgs.KeyboardDevice.Modifiers & ModifierKeys.Alt) == ModifierKeys.Alt; // We want to handle the ALT key. Get the real key if it is Key.System. Key key = keyArgs.Key; if (key == Key.System) { key = keyArgs.SystemKey; } // F4 alone or ALT+Up or ALT+Down will open the drop-down return ((key == Key.F4) && !isAltDown) || (((key == Key.Up) || (key == Key.Down)) && isAltDown); } return false; } #endregion #region Data private static Style _defaultElementStyle; private BindingBase _selectedValueBinding; private BindingBase _selectedItemBinding; private BindingBase _textBinding; #endregion } } // File provided for Reference Use Only by Microsoft Corporation (c) 2007. // Copyright (c) Microsoft Corporation. All rights reserved.
Link Menu
This book is available now!
Buy at Amazon US or
Buy at Amazon UK
- WeakReferenceEnumerator.cs
- ViewUtilities.cs
- SizeKeyFrameCollection.cs
- RecommendedAsConfigurableAttribute.cs
- TaiwanLunisolarCalendar.cs
- LookupNode.cs
- SynchronizationContext.cs
- DropDownList.cs
- XPathPatternBuilder.cs
- Paragraph.cs
- PrePostDescendentsWalker.cs
- WindowsToolbarItemAsMenuItem.cs
- ReverseInheritProperty.cs
- ToolStripProfessionalLowResolutionRenderer.cs
- QilList.cs
- AsyncCompletedEventArgs.cs
- QilUnary.cs
- SHA1Managed.cs
- objectresult_tresulttype.cs
- DataGridViewRowHeightInfoPushedEventArgs.cs
- DragEvent.cs
- mansign.cs
- AssemblyCollection.cs
- RequestCacheManager.cs
- TraversalRequest.cs
- ForceCopyBuildProvider.cs
- ToolStripLabel.cs
- CodeCommentStatement.cs
- WebBrowsableAttribute.cs
- ComponentEditorForm.cs
- EntityWithChangeTrackerStrategy.cs
- CqlIdentifiers.cs
- LinkedDataMemberFieldEditor.cs
- DbConnectionPool.cs
- ObjectListDataBindEventArgs.cs
- XPathQueryGenerator.cs
- BitmapEffectInputConnector.cs
- MouseEventArgs.cs
- ZipIOCentralDirectoryDigitalSignature.cs
- XmlSchemaSimpleContent.cs
- CTreeGenerator.cs
- pingexception.cs
- TiffBitmapDecoder.cs
- TransportManager.cs
- Range.cs
- WorkflowPrinting.cs
- ListDictionary.cs
- NamespaceCollection.cs
- DocumentPageView.cs
- PerfProviderCollection.cs
- Properties.cs
- Rijndael.cs
- TextReturnReader.cs
- ZipIOZip64EndOfCentralDirectoryBlock.cs
- EmptyImpersonationContext.cs
- ShutDownListener.cs
- ObfuscationAttribute.cs
- PathNode.cs
- RequiredAttributeAttribute.cs
- PropertyDescriptorCollection.cs
- QilLoop.cs
- unitconverter.cs
- XpsFixedPageReaderWriter.cs
- SafeBitVector32.cs
- EntityConnectionStringBuilder.cs
- StringPropertyBuilder.cs
- SystemMulticastIPAddressInformation.cs
- EntityUtil.cs
- Html32TextWriter.cs
- TypeHelpers.cs
- RadioButtonBaseAdapter.cs
- EmptyEnumerator.cs
- ProcessThreadCollection.cs
- AppPool.cs
- HtmlForm.cs
- NameValuePair.cs
- PrintPreviewControl.cs
- ResourceExpressionBuilder.cs
- HtmlTextArea.cs
- WindowsSysHeader.cs
- DataKeyArray.cs
- DataConnectionHelper.cs
- X509CertificateRecipientServiceCredential.cs
- KeyedQueue.cs
- UndoEngine.cs
- DbReferenceCollection.cs
- SplitterCancelEvent.cs
- assemblycache.cs
- DataSourceSelectArguments.cs
- RequestCacheEntry.cs
- PageThemeParser.cs
- PointHitTestResult.cs
- WebServiceReceive.cs
- ThreadAttributes.cs
- TemplateColumn.cs
- WebUtil.cs
- InstanceCollisionException.cs
- FormatSettings.cs
- HtmlControlPersistable.cs
- ObjectNavigationPropertyMapping.cs