// <copyright file="IdentificationCardTrackOne.cs" company="Scriptel Corporation">
//      Copyright 2014 - Scriptel Corporation
// </copyright>
namespace EasyScriptAPI
{
    using System;
    using System.Text;
    using System.Text.RegularExpressions;

    /// <summary>
    /// This class represents track one of the magnetic strip of an identification
    /// card, such as a United States drivers license.
    /// </summary>
    public class IdentificationCardTrackOne
    {
        /// <summary>
        /// card holder state
        /// </summary>  
        private string state;

        /// <summary>
        /// card holder city
        /// </summary>
        private string city;

        /// <summary>
        /// card holder last name
        /// </summary>
        private string lastName;

        /// <summary>
        /// card holder first name
        /// </summary>
        private string firstName;

        /// <summary>
        /// card holder middle name
        /// </summary>
        private string middleName;

        /// <summary>
        /// card holder address
        /// </summary>
        private string address;

        /// <summary>
        /// vendor-specific discretionary data
        /// </summary>
        private string discretionaryData = "";

        /// <summary>
        /// This method attempts to parse the first track of data out of a magnetic
        /// strip string.
        /// </summary>
        /// <param name="trackData">data to parse from</param>
        /// <returns>IdentificationCardTrackOne if data can be parsed, null otherwise.</returns>
        public static IdentificationCardTrackOne Parse(string trackData)
        {
            Regex regex = new Regex(".*\\%([A-Z]{2})([A-Z\\.\\-' ]{1,13})\\^?([A-Z\\.\\-' \\$]{1,35})\\^?([^\\?^\\^]{1,29})\\^?\\?.*");
            Match m = regex.Match(trackData);
            if (m.Success)
            {
                IdentificationCardTrackOne track = new IdentificationCardTrackOne();
                track.SetState(m.Groups[1].Value);
                track.SetCity(m.Groups[2].Value);
                track.SetAddress(m.Groups[4].Value);

                char[] splitParams = new char[1];
                splitParams[0] = '$';
                string[] nameBits = m.Groups[3].Value.Split(splitParams);
                if (nameBits.Length > 0)
                {
                    track.SetLastName(nameBits[0]);
                }
                if (nameBits.Length > 1)
                {
                    track.SetFirstName(nameBits[1]);
                }

                if (nameBits.Length > 2)
                {
                    track.SetMiddleName(nameBits[2]);
                }

                return track;
            }

            return null;
        }

        /// <summary>
        /// Returns this object as a human readable string.
        /// </summary>
        /// <returns>This object as a human readable string.</returns>
        public override string ToString()
        {
            StringBuilder sb = new StringBuilder();
            string ln = Environment.NewLine;
            sb.Append("Identification Card - Track One:").Append(ln);
            sb.Append("             State: ").Append(this.state).Append(ln);
            sb.Append("              City: ").Append(this.city).Append(ln);
            sb.Append("        First Name: ").Append(this.firstName).Append(ln);
            sb.Append("       Middle Name: ").Append(this.middleName).Append(ln);
            sb.Append("         Last Name: ").Append(this.lastName).Append(ln);
            sb.Append("        Expiration: ").Append(this.address).Append(ln);
            sb.Append("Discretionary Data: ").Append(this.discretionaryData).Append(ln);
            return sb.ToString();
        }

        /// <summary>
        /// Gets the card holders state
        /// </summary>
        /// <returns>card holders state</returns>
        public string GetState()
        {
            return this.state;
        }

        /// <summary>
        /// Gets the card holders city
        /// </summary>
        /// <returns>card holders city</returns>
        public string GetCity()
        {
            return this.city;
        }
        
        /// <summary>
        /// Gets the card holders last name
        /// </summary>
        /// <returns>card holders last name</returns>
        public string GetLastName()
        {
            return this.lastName;
        }

        /// <summary>
        /// Gets the card holders middle name
        /// </summary>
        /// <returns>card holders middle name</returns>
        public string GetMiddleName()
        {
            return this.middleName;
        }
        
        /// <summary>
        /// Gets the card holders first name
        /// </summary>
        /// <returns>card holders first name</returns>
        public string GetFirstName()
        {
            return this.firstName;
        }

        /// <summary>
        /// Gets the card holders address
        /// </summary>
        /// <returns>card holders address</returns>
        public string GetAddress()
        {
            return this.address;
        }

        /// <summary>
        /// Gets the vendor specific discretionary data
        /// </summary>
        /// <returns>vendor specific discretionary data</returns>
        public string GetDiscretionaryData()
        {
            return this.discretionaryData;
        }

        /// <summary>
        /// Sets the card holders first name
        /// </summary>
        /// <param name="firstName">card holders first name</param>
        private void SetFirstName(string firstName)
        {
            this.firstName = firstName;
        }

        /// <summary>
        /// Sets the card holders last name.
        /// </summary>
        /// <param name="lastName">card holders last name.</param>
        private void SetLastName(string lastName)
        {
            this.lastName = lastName;
        }

        /// <summary>
        /// Sets the card holders address
        /// </summary>
        /// <param name="address">card holders address</param>
        private void SetAddress(string address)
        {
            this.address = address;
        }

        /// <summary>
        /// Sets the card holders state
        /// </summary>
        /// <param name="state">card holders state</param>
        private void SetState(string state)
        {
            this.state = state;
        }

        /// <summary>
        /// Sets the card holders city
        /// </summary>
        /// <param name="city">card holders city</param>
        private void SetCity(string city)
        {
            this.city = city;
        }

        /// <summary>
        /// Sets the card holders middle name
        /// </summary>
        /// <param name="middleName">card holders middle name</param>
        private void SetMiddleName(string middleName)
        {
            this.middleName = middleName;
        }
    }
}
