Search code examples
c#datetimepicker

Databound DateTimePicker Time in C#


I'm have a Windows Form with 2 datetimepicker controls: one for date and a separate datetimepicker control for time. Both of these controls are bound to the same column in a database and the controls have different property names (i.e., dateEdit and timeEdit) and different formats (i.e., Long and Time).

Here are my problems/questions:

  1. The timeEdit picker ignores whatever seconds are in the database entry and sets the time seconds to "00", as in "2:34:00", even though the database entry (trimmed to time for this illustration) is "14:34:31.891123 -04:00". How can I get the seconds to correctly display?
  2. Whenever I edit the seconds in the timeEdit picker from "00" to (for example) "15", as in "2:34:15", the picker resets the seconds to "00" before passing the value to the next function. How do I pass the correct seconds value?
  3. I'd like to edit the milliseconds on the time. Is it best for me to bind the trimmed milliseconds (using DATEPART) to a text box? Will I need to convert or cast the milliseconds to a char or string in order to correctly display them in a text box?

Thanks for any help!

Code to trigger the edit form:

    private void timeDataGridView_CellContentClick(object sender, DataGridViewCellEventArgs e)
    {
        try
        {
            if (e.ColumnIndex == 5)
            {
                EditTime editForm = new EditTime((Guid)timeDataGridView.Rows[e.RowIndex].Cells[e.ColumnIndex].Value);

                editForm.StartPosition = FormStartPosition.CenterScreen;
                editForm.ShowDialog();
                editForm.Close();
            }
        }
        catch (Exception ex)
        {
            string msg = "Error: ";
            msg += ex.Message;
            throw new Exception(msg);
        }
    }

Code for the form:

    using System;
    using System.Collections.Generic;
    using System.ComponentModel;
    using System.Configuration;
    using System.Data;
    using System.Data.SqlClient;
    using System.Drawing;
    using System.Linq;
    using System.Text;
    using System.Windows.Forms;

    namespace StatusManager
    {
        public partial class EditTime : Form
        {
            private Guid calendarId;

            public EditTime()
            {
                InitializeComponent();
            }

            public EditTime(Guid Id)
            {
                InitializeComponent();
                calendarId = Id;
            }

            public string GetConnectionString()
            {
                var connString = ConfigurationManager.ConnectionStrings["StatusManager.Properties.Settings.StatusConnectionString"].ConnectionString;
                return connString;
            }

            private void UpdateCalendarItem(string dateEdit, string timeEdit, string note)
            {
                var conn = new SqlConnection(GetConnectionString());

                const string UpdateStatusSql = @"UPDATE dbo.statuses SET
                calendarTime = @timeOffset
                notes = @note 
                WHERE PK_calendarUID = @PK_calendarUID";

                try
                {
                    SqlCommand cmd = new SqlCommand(UpdateSql, conn);
                    var param = new SqlParameter[3];

                    param[0] = new SqlParameter("@PK_calendarUID", calendarId);

                    //Convert date(s) to correct format
                    string dateTimeCombined = dateEdit + " " timeEdit;
                    DateTime timeConverted = Convert.ToDateTime(dateTimeCombined);
                    DateTimeOffset timeOffset = new DateTimeOffset(timeConverted);

                    param[1] = new SqlParameter("@timeOffset", timeOffset);
                    param[2] = new SqlParameter("@note", note);

                    foreach (SqlParameter t in param)
                    {
                        cmd.Parameters.Add(t);
                    }

                    conn.Open();
                    cmd.CommandType = CommandType.Text;
                    cmd.ExecuteNonQuery();
                }
                catch (SqlException ex)
                {
                    string msg = "Error updating 'calendarItems': ";
                    msg += ex.Message;
                    throw new Exception(msg);
                }
                finally
                {
                    conn.Close();
                }          
            }

            private void editTimeButton_Click(object sender, EventArgs e)
            {
                UpdateCalendarItem(dateEdit.Text, timeEdit.Text, notes.Text);

                this.Close();
            }

            private void EditTime_Load(object sender, EventArgs e)
            {
                this.locationsTableAdapter.Fill(this.locationsDataSet.locations);
                this.calendarTableAdapter.FillById(this.calendarDataSet.calendarItems, calendarId);
            }
        }
    }

Code for instantiating the datetimepicker:

    this.timeEdit.CustomFormat = "";
    this.timeEdit.DataBindings.Add(new System.Windows.Forms.Binding("Text", this.calendarBindingSource, "calendarTime", true));
    this.timeEdit.Format = System.Windows.Forms.DateTimePickerFormat.Time;
    this.timeEdit.Location = new System.Drawing.Point(385, 30);
    this.timeEdit.Name = "timeEdit";
    this.timeEdit.ShowUpDown = true;
    this.timeEdit.Size = new System.Drawing.Size(89, 20);
    this.timeEdit.TabIndex = 2;

Solution

  • Problem solved but I'm not exactly sure how. Here's what I did:

    1. In calendarDataSet, I updated both queries (Fill,GetData and FillById,GetDataBy (@ID)) to select calendarTime as CONVERT(VARCHAR(12), calendarTime, 114) AS calHoursMinsSec
    2. In essence, I created created a new column with the hours, minutes, seconds, and milliseconds
    3. On the form, I added a textbox and bound the textbox to calHoursMinsSec

    Note: My previous attempts to convert the datetime to a varchar to were unsuccessful no doubt due to operator error.

    Once I saved the form, the binding seemed to stick and I was able to pass the relevant variables to the update function

    Thanks for everyone's input! I appreciate the guidance and suggestions!