Introduction
This article addresses the construction of a custom control that will convert UNIX time into useful and readable dates for display in a WinForms application. The control will accept either a standard date or UNIX time value and can convert the value in either direction (From UNIX Time to Date or from Date to UNIX Time).
Figure 1: The test application running.
The control contains two properties that may be set to control the displayed output and the usability of the control. The “Convert On Click” property will enable or disable the control’s ability to convert the value back and forth between UNIX time and normal date when a user clicks on the control; this may be useful if you wish to permit the user to edit the value in one format and view it in another. The other property is “Direction”. Direction is used to determine whether or not the control will display the value as UNIX time or as a standard date.
Getting Started
In order to get started, unzip the included project and open the solution in the Visual Studio 2008 environment. In the solution explorer, you should note these files (Figure 2):
Figure 2: Solution Explorer.
As you can see from Figure 2, there are two projects. UnixTime
is the custom control project and it contains a single custom control (UTConverter.cs). The second project (ControlTest
) is a WinForms application used to test the control.
The Custom Control (UTConverter.cs)
The custom control is a class that extends the standard TextBox
control.
The code is pretty simple. If you'd care to open the code view up in the IDE, you will see that the code file begins with the following library imports:
using System;
using System.ComponentModel;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
Following the imports, the namespace and class are defined:
namespace UnixTime
{
public partial class UTConverter : TextBox
{
Next an enumeration is defined; this enumeration is entitled Direction
. The enumeration is used to define whether or not the date displayed in the extended textbox
control will display dates or UNIX time stamp values. UNIX time stamp values can be defined as the number of seconds before or after the date 1/1/1970. Following the declaration of the enumeration, two private
member variables are defined; one to keep track of the selected Direction
option, and one Boolean value used to determine whether or not “Convert On Click” is enabled.
#region Members
public enum Direction
{
ToUnix,
ToDate
}
private Direction mCurrentDirection;
private bool mConvertOnClick;
#endregion
Next, a constructor is defined; within the constructor, the default values for the control are set by setting the CurrentDirection
property to Direction.ToDate
, and setting the ConvertOnClick
property to true
. In this default condition, the control will normally display the date as a date and will, on click, convert the date back to the UNIX time stamp value.
#region Constructor
public UTConverter()
{
InitializeComponent();
CurrentDirection = Direction.ToDate;
ConvertOnClick = true;
}
#endregion
After the constructor, a region is setup to contain the control’s added properties. The first property is CurrentDirection
; it provides public
access to the mCurrentDirection
member variable used to determine whether or not the control will display its value as a date or as a UNIX time stamp value. The other property, ConvertOnClick
, is used to enable or display the functionality that will convert between UNIX and normal date displays within the control at runtime.
#region Properties
[CategoryAttribute("UNIX Time"),
Browsable(true),
BindableAttribute(false),
DescriptionAttribute("Convert to or from UNIX time.")]
public Direction CurrentDirection
{
get
{
return mCurrentDirection;
}
set
{
mCurrentDirection = value;
}
}
[CategoryAttribute("UNIX Time"),
Browsable(true),
BindableAttribute(false),
DescriptionAttribute("Enable or disable On Click UNIX Time format
conversion.")]
public bool ConvertOnClick
{
get
{
return mConvertOnClick;
}
set
{
mConvertOnClick = value;
}
}
#endregion
The next region defined is entitled Methods
; this section carries the code used to provide the UNIX-Date conversion functionality to this custom control.
#region Methods
The ConvertToDateTime
function converts the Unix time stamp to a short date string
; this is easily accomplished by adding the number of seconds provided to the baseline data used for the UNIX time stamp.
private void ConvertToDateTime(double unixTime)
{
DateTime convertedDateTime =
new DateTime(1970,1,1,0,0,0).AddSeconds(unixTime);
this.Text = convertedDateTime.ToShortDateString();
}
The next function converts a date (as a short date string) to UNIX time format:
private void ConvertToUnixTime(DateTime dt)
{
this.Text = (dt - new
DateTime(1970,1,1,0,0,0)).TotalSeconds.ToString();
}
The controls validated event handler is used to update the display of the date or UNIX time value based upon whether or not the control’s CurrentDirection
property has been set to display dates or UNIX time.
private void UTConverter_Validated(object sender, EventArgs e)
{
try
{
if (mCurrentDirection == Direction.ToDate)
{
ConvertToDateTime(Convert.ToDouble(this.Text));
}
else
{
ConvertToUnixTime(Convert.ToDateTime(this.Text));
}
}
catch { }
}
The key press event handler is configured to disregard non-numeric values that may be typed into the control. The control accepts digits, control characters, and the minus key. Limiting the key press in this way will allow the user to enter numbers and to use the backspace key, and to enter a minus sign to enter dates less than 1/1/1970 when working with UNIX times.
private void UTConverter_KeyPress(object sender, KeyPressEventArgs e)
{
if (!char.IsDigit(e.KeyChar) &&
!char.IsControl(e.KeyChar) &&
e.KeyChar != '-')
{
e.Handled = true;
}
}
The next bit of code just repeats the call to update the displayed value whenever the user exits, enters, or refreshes the textbox
.
private void UTConverter_Leave(object sender, EventArgs e)
{
try
{
if (mCurrentDirection == Direction.ToDate)
{
ConvertToDateTime(Convert.ToDouble(this.Text));
}
else
{
ConvertToUnixTime(Convert.ToDateTime(this.Text));
}
}
catch { }
}
private void UTConverter_Enter(object sender, EventArgs e)
{
try
{
if (ConvertOnClick)
{
if (mCurrentDirection == Direction.ToDate)
{
ConvertToUnixTime(Convert.ToDateTime(this.Text));
}
else
{
ConvertToDateTime(Convert.ToDouble(this.Text));
}
}
}
catch { }
}
public override void Refresh()
{
base.Refresh();
try
{
if (mCurrentDirection == Direction.ToDate)
{
ConvertToDateTime(Convert.ToDouble(this.Text));
}
else
{
ConvertToUnixTime(Convert.ToDateTime(this.Text));
}
}
catch { }
}
#endregion
}
}
That wraps the content of the control. The next section will discuss the demonstration project.
The Main Form (Form1.cs from the Control Test Project)
The test form contains eight instances of the custom control; each one is used to display something different. Four are loaded using a short date string
and four are loaded using a UNIX time stamp. In both groups, each of the controls is set up with the ConvertOnClick
method enabled and disabled, and with the Direction
option set to either ToDate
or ToUnix
. A tooltip was added to the form and it is set to describe something about each of the options selected when the user hovers over the control.
The code for the form is presented in its entirety below. The code in the form load event handler is annotated to describe what each section accomplishes.
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
namespace ControlTest
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
private void button1_Click(object sender, EventArgs e)
{
this.Dispose();
}
private void Form1_Load(object sender, EventArgs e)
{
utConverter1.Text = "-885772800";
utConverter2.Text = "849312000";
utConverter3.Text = "999648000";
utConverter4.Text = "4000000000";
utConverter5.Text = "7/19/1960";
utConverter6.Text = "5/16/1933";
utConverter7.Text = "7/4/2008";
utConverter8.Text = "6/18/3100";
utConverter1.Refresh();
utConverter2.Refresh();
utConverter3.Refresh();
utConverter4.Refresh();
utConverter5.Refresh();
utConverter6.Refresh();
utConverter7.Refresh();
utConverter8.Refresh();
button1.Select();
}
}
}
Summary
This article is intended to describe a custom control with the very specific purpose of converting values between UNIX time stamp format and a normal short date string
. In that, the project is an easy example describing how one might go about creating a custom control to solve a problem and one may use a similar approach to other situations where a custom control might be a handy alternative to using an existing control along with additional code to attain similar results.
History
- 3rd June, 2008: Initial post