﻿
/*==============================================================================Application:    Utility FunctionAuthor:         John GardnerVersion:        V1.0Date:           18th November 2003Description:    Used to check the validity of a UK postcodeVersion:        V2.0Date:           8th March 2005Description:    BFPO postcodes implemented.                The rules concerning which alphabetic characters are allowed in                 which part of the postcode were more stringently implementd.Version:        V3.0Date:           8th August 2005Description:    Support for Overseas Territories added                 
Version:        V3.1Date:           23rd March 2008Description:    Problem corrected whereby valid postcode not returned, and                 'BD23 DX' was invalidly treated as 'BD2 3DX' (thanks Peter Graves)        
Version:        V4.0Date:           7th October 2009Description:    Character 3 extended to allow 'pmnrvxy' (thanks to Jaco de Groot)            Parameters:     toCheck - postcodeto be checked. 
This function checks the value of the parameter for a valid postcode format. The space between the inward part and the outward part is optional, although is inserted if not there as it is part of the official postcode.
If the postcode is found to be in a valid format, the function returns the postcode properly formatted (in capitals with the outward code and the inwardcode separated by a space. If the postcode is deemed to be incorrect a value of false is returned.
Example call:if (checkPostCode (myPostCode)) {alert ("Postcode has a valid format")} else {alert ("Postcode has invalid format")};------------------------------------------------------------------------------*/

function checkPostCode(toCheck) {

    // Permitted letters depend upon their position in the postcode.
    var alpha1 = "[abcdefghijklmnoprstuwyz]";                       // Character 1
    var alpha2 = "[abcdefghklmnopqrstuvwxy]";                       // Character 2
    var alpha3 = "[abcdefghjkpmnrstuvwxy]";                         // Character 3
    var alpha4 = "[abehmnprvwxy]";                                  // Character 4
    var alpha5 = "[abdefghjlnpqrstuwxyz]";                          // Character 5

    // Array holds the regular expressions for the valid postcodes
    var pcexp = new Array();

    // Expression for postcodes: AN NAA, ANN NAA, AAN NAA, and AANN NAA
    pcexp.push(new RegExp("^(" + alpha1 + "{1}" + alpha2 + "?[0-9]{1,2})(\\s*)([0-9]{1}" + alpha5 + "{2})$", "i"));

    // Expression for postcodes: ANA NAA
    pcexp.push(new RegExp("^(" + alpha1 + "{1}[0-9]{1}" + alpha3 + "{1})(\\s*)([0-9]{1}" + alpha5 + "{2})$", "i"));

    // Expression for postcodes: AANA  NAA
    pcexp.push(new RegExp("^(" + alpha1 + "{1}" + alpha2 + "{1}" + "?[0-9]{1}" + alpha4 + "{1})(\\s*)([0-9]{1}" + alpha5 + "{2})$", "i"));

    // Exception for the special postcode GIR 0AA
    pcexp.push(/^(GIR)(\s*)(0AA)$/i);

    // Standard BFPO numbers
    pcexp.push(/^(bfpo)(\s*)([0-9]{1,4})$/i);

    // c/o BFPO numbers
    pcexp.push(/^(bfpo)(\s*)(c\/o\s*[0-9]{1,3})$/i);

    // Overseas Territories
    pcexp.push(/^([A-Z]{4})(\s*)(1ZZ)$/i);

    // Load up the string to check
    var postCode = toCheck;

    // Assume we're not going to find a valid postcode
    var valid = false;

    // Check the string against the types of post codes
    for (var i = 0; i < pcexp.length; i++) {
        if (pcexp[i].test(postCode)) {

            // The post code is valid - split the post code into component parts
            pcexp[i].exec(postCode);

            // Copy it back into the original string, converting it to uppercase and
            // inserting a space between the inward and outward codes
            postCode = RegExp.$1.toUpperCase() + " " + RegExp.$3.toUpperCase();

            // If it is a BFPO c/o type postcode, tidy up the "c/o" part
            postCode = postCode.replace(/C\/O\s*/, "c/o ");

            // Load new postcode back into the form element
            valid = true;

            // Remember that we have found that the code is valid and break from loop
            break;
        }
    }

    // Return with either the reformatted valid postcode or the original invalid 
    // postcode
    if (valid) { return postCode; } else return false;
}
