2013-07-17 20 views
0

我一直在玩一些示例代碼,它爲DataGridView實現了一個datepicker列。DataGridView自定義列在運行時訪問設計時間參數

我在哪裏掙扎的是如何在CalendarEditingControl中正確地訪問設計時間參數(感謝Bradley Smith提供了關於覆蓋Clone方法的提示),我想將Format設置爲DateFormat。

我在下面提供了完整的示例,並看到我想要使用日期格式,如果你只是掃描註釋: // * ** * ** * ** * *我想格式設置爲這裏設計時提供價值inDataGridViewCalendarColumn.DateFormat * ** * ** * ** * * //

感謝

馬特

使用系統;使用System.Windows.Forms的 ;

命名空間MyApplication.Components { 公共類DataGridViewCalendarColumn:的DataGridViewColumn { 公共DataGridViewCalendarColumn() :基座(新CalendarCell()){ }

public override DataGridViewCell CellTemplate 
    { 
     get 
     { 
      return base.CellTemplate; 
     } 
     set 
     { 
      // Ensure that the cell used for the template is a CalendarCell. 
      if (value != null && 
       !value.GetType().IsAssignableFrom(typeof(CalendarCell))) 
      { 
       throw new InvalidCastException("Must be a CalendarCell"); 
      } 
      base.CellTemplate = value; 

     } 
    } 

    public DateTimePickerFormat DateFormat { get; set; } 

    public override object Clone() 
    { 
     DataGridViewCalendarColumn clone = (DataGridViewCalendarColumn)base.Clone(); 
     clone.DateFormat = this.DateFormat; 
     return clone; 
    } 

} 

public class CalendarCell : DataGridViewTextBoxCell 
{ 

    public CalendarCell(): base() 
    { 
     // Use the short date format. 
     this.Style.Format = "d"; 
    } 

    public override void InitializeEditingControl(int rowIndex, object initialFormattedValue, DataGridViewCellStyle dataGridViewCellStyle) 
    { 
     // Set the value of the editing control to the current cell value. 
     base.InitializeEditingControl(rowIndex, initialFormattedValue, 
      dataGridViewCellStyle); 
     CalendarEditingControl ctl = 
      DataGridView.EditingControl as CalendarEditingControl; 
     // Use the default row value when Value property is null. 
     if (this.Value == null) 
     { 
      ctl.Value = (DateTime)this.DefaultNewRowValue; 
     } 
     else 
     { 
      ctl.Value = (DateTime)this.Value; 
     } 
    } 

    public override Type EditType 
    { 
     get 
     { 
      // Return the type of the editing control that CalendarCell uses. 
      return typeof(CalendarEditingControl); 
     } 
    } 

    public override Type ValueType 
    { 
     get 
     { 
      // Return the type of the value that CalendarCell contains. 

      return typeof(DateTime); 
     } 
    } 

    public override object DefaultNewRowValue 
    { 
     get 
     { 
      // Use the current date and time as the default value. 
      return DateTime.Now; 
     } 
    } 


} 

class CalendarEditingControl : DateTimePicker, IDataGridViewEditingControl 
{ 
    DataGridView dataGridView; 
    private bool valueChanged = false; 
    int rowIndex; 

    public CalendarEditingControl() 
    { 
     //*********************** I'd like to set the Format to the design time value provided inDataGridViewCalendarColumn.DateFormat here ***********************// 
     //(instead of hard coding it to DateTimePickerFormat.Short) 
     this.Format = DateTimePickerFormat.Short; 
    } 

    // Implements the IDataGridViewEditingControl.EditingControlFormattedValue 
    // property. 
    public object EditingControlFormattedValue 
    { 
     get 
     { 
      return this.Value.ToShortDateString(); 
     } 
     set 
     { 
      if (value is String) 
      { 
       try 
       { 
        // This will throw an exception of the string is 
        // null, empty, or not in the format of a date. 
        this.Value = DateTime.Parse((String)value); 
       } 
       catch 
       { 
        // In the case of an exception, just use the 
        // default value so we're not left with a null 
        // value. 
        this.Value = DateTime.Now; 
       } 
      } 
     } 
    } 

    // Implements the 
    // IDataGridViewEditingControl.GetEditingControlFormattedValue method. 
    public object GetEditingControlFormattedValue(
     DataGridViewDataErrorContexts context) 
    { 
     return EditingControlFormattedValue; 
    } 

    // Implements the 
    // IDataGridViewEditingControl.ApplyCellStyleToEditingControl method. 
    public void ApplyCellStyleToEditingControl(
     DataGridViewCellStyle dataGridViewCellStyle) 
    { 
     this.Font = dataGridViewCellStyle.Font; 
     this.CalendarForeColor = dataGridViewCellStyle.ForeColor; 
     this.CalendarMonthBackground = dataGridViewCellStyle.BackColor; 
    } 

    // Implements the IDataGridViewEditingControl.EditingControlRowIndex 
    // property. 
    public int EditingControlRowIndex 
    { 
     get 
     { 
      return rowIndex; 
     } 
     set 
     { 
      rowIndex = value; 
     } 
    } 

    // Implements the IDataGridViewEditingControl.EditingControlWantsInputKey 
    // method. 
    public bool EditingControlWantsInputKey(
     Keys key, bool dataGridViewWantsInputKey) 
    { 
     // Let the DateTimePicker handle the keys listed. 
     switch (key & Keys.KeyCode) 
     { 
      case Keys.Left: 
      case Keys.Up: 
      case Keys.Down: 
      case Keys.Right: 
      case Keys.Home: 
      case Keys.End: 
      case Keys.PageDown: 
      case Keys.PageUp: 
       return true; 
      default: 
       return !dataGridViewWantsInputKey; 
     } 
    } 

    // Implements the IDataGridViewEditingControl.PrepareEditingControlForEdit 
    // method. 
    public void PrepareEditingControlForEdit(bool selectAll) 
    { 
     // No preparation needs to be done. 
    } 

    // Implements the IDataGridViewEditingControl 
    // .RepositionEditingControlOnValueChange property. 
    public bool RepositionEditingControlOnValueChange 
    { 
     get 
     { 
      return false; 
     } 
    } 

    // Implements the IDataGridViewEditingControl 
    // .EditingControlDataGridView property. 
    public DataGridView EditingControlDataGridView 
    { 
     get 
     { 
      return dataGridView; 
     } 
     set 
     { 
      dataGridView = value; 
     } 
    } 

    // Implements the IDataGridViewEditingControl 
    // .EditingControlValueChanged property. 
    public bool EditingControlValueChanged 
    { 
     get 
     { 
      return valueChanged; 
     } 
     set 
     { 
      valueChanged = value; 
     } 
    } 

    // Implements the IDataGridViewEditingControl 
    // .EditingPanelCursor property. 
    public Cursor EditingPanelCursor 
    { 
     get 
     { 
      return base.Cursor; 
     } 
    } 

    protected override void OnValueChanged(EventArgs eventargs) 
    { 
     // Notify the DataGridView that the contents of the cell 
     // have changed. 
     valueChanged = true; 
     this.EditingControlDataGridView.NotifyCurrentCellDirty(true); 
     base.OnValueChanged(eventargs); 
    } 
} 

}

回答

0

Winforms中(以及WebForms和WPF ...),您無法訪問構造函數中的設計時值。相反,框架會調用您的無參數構造函數,然後在您的對象上使用適當的屬性設置器來完成它的初始化。

在設計器用戶沒有在設計時指定所有屬性值應該是什麼的情況下,在構造器中設置對象屬性的默認值是一個明智的做法。所以你的構造函數很好。

1

您需要做的就是將列中的DateFormat屬性應用到編輯控件上。在InitializeEditingControl方法中,添加以下行:

ctl.Format = (OwningColumn as DataGridViewCalendarColumn).DateFormat; 

這應該做的伎倆。

+0

謝謝布拉德利,那太好了。最後一個障礙是我在多列中使用自定義列,例如開始日期和結束日期,並添加了一個額外的DefaultDate屬性。發生的情況是,即使將這兩列設置爲不同的值,兩列也會得到相同的值。我是否需要管理一系列值或者是否有更優雅的方式? – mattpm

+0

@mattpm你的意思是相同的DateFormat值或相同的DateTime值? –

+0

我的意思是相同的DateTime值。我已通過將代碼行 ctl.DefaultDate =(OwningColumn as DataGridViewCalendarColumn).DefaultDate解決了它; 之前行 基地。InitializeEditingControl(rowIndex,initialFormattedValue,dataGridViewCellStyle); – mattpm

相關問題