
function cap(s){
	return s.substring(0,1).toUpperCase() + s.substring(1,s.length);
}
function list(a)
{
	var s = "";
	for( var i=0; i<a.length; i++)
	{
		if( i == a.length - 1 )		
			s += " and " + a[i][0] + " " + pluralize({count: a[i][0], singular: a[i][1]});
		else
			s += a[i][0] + " " + pluralize({count: a[i][0], singular: a[i][1]}) + ", ";		
	}
	return s;
}
function isPrime(x)
{
	if( x % 2 == 0 )
		return false;
	if( x % 3 == 0 )
		return false;
	if( x % 5 == 0 )
		return false;
	if( x % 7 == 0 )
		return false;
	if( x % 11 == 0 )
		return false;
	if( x % 13 == 0 )
		return false;
	if( x % 17 == 0 )
		return false;
	if( x % 19 == 0 )
		return false;
	if( x % 23 == 0 )
		return false;
	//jeash, I guess this thing's prime (ish)!
	return true;
}
function isWhole(d)
{
	return Math.round(d) == d;
}
function terminating(d)
{	
	if(isWhole(d))
		return true;
	var s = d.toString();
	s = s.split('.');
	return s[1].length < 4;
}
function deg(x)
{
	return x + "&deg; ";
}
function makeMoney(a)
{
	if(typeof(a)=="string")
	{
		return a + " of a dollar ";
	}
	var DecimalSeparator = Number("1.2").toLocaleString().substr(1,1);
	var AmountWithCommas = a.toLocaleString();
	var arParts = String(AmountWithCommas).split(DecimalSeparator);
	var intPart = arParts[0];
	var decPart = (arParts.length > 1 ? arParts[1] : '');
	decPart = (decPart + '00').substr(0,2);
	return '$' + intPart + DecimalSeparator + decPart;
}
function close(x,i)
{
	var fin = 0;
	if( i == undefined )
		i = false;
	var d = x * 0.2;
	if( fifty() )
		fin = x - d;	
	else
		fin = x + d;	 

	if( i )
		fin = Math.round(fin);
		
	return fin;
}
function edit(s)
{
	return "<p class='edit'>" + s + "</p>";
}
function adjective()
{
	var adjectives=new Array("grey","large","yellow", "purple", "small", "colorful", "long");
	var x = Math.floor(Math.random() * adjectives.length);
	return " " + adjectives[x];
}
function color()
{
	var adjectives=new Array("grey","blue","yellow", "purple", "red", "black", "white");
	var x = Math.floor(Math.random() * adjectives.length);
	return " " + adjectives[x];
}
function verb(s)
{
	var v = "";
  	$.ajax({
         url:    'http://www.automathmagic.com/ajaxGetVerb.php',
	     data: ({add: s}),         
		 beforeSend: function(XMLHttpRequest) {
				loadShow();
		},
         success: function(data) {		           		 
					v = data; 
				loadHide();	
         		 },
         async:   false
    });
	return pad(v);
}
function pad(s)
{
	return " " + s + " ";
}
function noun(c,t,f)
{
	if( t == undefined )
		t = 0;
	if( c == undefined )
		c = 1;
	if( f == undefined )
		f = 0;
  	var n;
  	$.ajax({
         url:    'http://www.automathmagic.com/ajaxGetNoun.php',
	     data: ({ shape: t, fractional: f }), 
		 beforeSend: function(XMLHttpRequest) {
				loadShow();
		},
         success: function(data) {		           		 
				n = new thing(data,c); 
				loadHide();	
         		 },
         async:   false
    });
	return n;
}
thing.prototype.toString = function nounPrint() 
{
  return this.noun;
};

function posessive(s)
{
	if( s.charAt((s.length-1)) == 's' )
		return s + "' ";
	else
		return s + "'s ";
}

function rectangleNoun()
{
	return noun(1,2);
}

function loadShow()
{
	$('#loader').show();
}

function loadHide()
{
	$('#loader').hide();
	console.log("Loaded");	
}

  function getPerson()
  { 
  		var p = "";
	  	$.ajax({
	         url:    'http://www.automathmagic.com/getPerson.php',
			 beforeSend: function(XMLHttpRequest) {
				loadShow();
			},	
	         success: function(data) {		  
	         		 	p = new peep(data);
	         		 	loadHide();
	         		 },
	         async:   false
	    });          
	    return p;
  }
  peep.prototype.toString = function personPrint() {
  return this.name;
};
function thing(s,n)
{
	if( n == undefined )
		n = 1;
	var a = new Array(); 
	a = s.split('\n'); 
	this.noun = pluralize({count: n, singular: a[0]});
	this.perimeter = a[1];
	this.area = a[2];	
}

function peep(s)
{
	var a = new Array();
	a = s.split('\n'); 
	this.name= a[0];
	this.pronoun= a[1];
	this.posessive = a[2];
}
function person(s)
{
	return getPerson();
}

function circleNoun()
{
	return noun(1,1);
}
function verbNoun()
{
	var n=new Array("eat","paint","walk","build", "sew");
	var m=new Array("cookies","paintings","miles", "cars", "shirts");
	var x = Math.floor(Math.random() * n.length);
	var z = new Array(n[x],m[x]);
	return z;
}
function triangleNoun()
{
	var n=new Array("triangular garden", "triangular slice of pizza", "triangular window");
	var m=new Array("grass","cheese","glass");
	var o=new Array("fence","crust","frame");
	var x = Math.floor(Math.random() * n.length);
	var z = new Array(n[x],m[x],o[x]);
	return z;
}

function isMultipleOf(x,y)
{
	if( x % y == 0 )
		return true;
	else if( y % x == 0 )
		return true;
	else
		return false;
}

function measurement(sys,size,n)
{
	
	if( n == undefined)
	{
		n = 2;
	}
	if( sys == "us" )
	{
		if(size == "small")
		{
			if( n > 1)
				return " inches";
			else
				return " inch";
		}
		else
		{
			if( n > 1)
				return " feet";
			else
				return " foot";

		}
	}
	else
	{
		if(size == "small")
		{
			if( n > 1)
				return " cenimeters";
			else
				return " cenimeter";

		}
		else
		{
			if( n > 1)
				return " meters";
			else
				return " meter";

		}
	}
}


function random(n,m)
{
	if( m == undefined )
		m = 1;
	return Math.floor(Math.random()*n) + m;
}

function fifty()
{
	return random(100) > 50;
}

function operation(handicap)
{
	if( handicap == undefined )
	{	
		handicap = false;
	}
  	var operation = random(4);
	if( handicap )
	{
		if( operation < 3 )
			return "*";
		else
			return "/";
	}
	else
	{
  		 switch(operation)
  		 {
  		 	case 1:
				return "+"; 
			case 2:
			 	return "-"; 
			case 3:
		 		return "*"; 
		 	case 4:
		 		return "/";
			default:
				return "";
		}
	}			
	return "";
}
 function countLetters(stringy) 
 {
	var tally=new Object();
	for( var i=0; i<stringy.length;i++)
	{
		var c=stringy.charAt(i);
		tally[c]=(tally[c]|0)+1;
	}
	return tally;
 }

 function fraction(dec)
 {
	 var decString = dec.toString();
	 var dslength = decString.length - 1;
	 var div = 1;
	 // Multiply by powers of 10 to remove the decimal
	if( dslength > 6 )
	{
		return "about " + round(dec) + " (<em>sorry</em>)";
	}
	for (i=0; i<dslength; i++)
	 {
	  dec = dec * 10;
	  div = div * 10;
	 }
	 // Factor out the GCF of the two numbers
	 for (i=2; i <= dec; i++) {
	      while ((mod(dec,i) == 0) && (mod(div,i) == 0))
	      {
	          dec = dec/i;
	            div = div/i;            
	      }
	 }
	 if( div == 1 )
	 {
	 	return dec;
	 }
 // Display the two numbers in the fraction form boxes and in the verification form.
 return formatFraction(dec,div);
}

function reduce(num, den)
 {
 // Factor out the GCF of the two numbers
 for (i=2; i <= num; i++) {
      while ((mod(den,i) == 0) && (mod(num,i) == 0))
      {
          den = den/i;
            num = num/i;            
      }
 }
 if( den == 1 )
 {
 return num;
 }
 // Display the two numbers in the fraction form boxes and in the verification form.
 return formatFraction(num,den);
}
function areaRectangle(l, w)
{
	return l * w;
}
function areaCircle(r)
{
	return r * r * 3.14;
}
function areaTriangle(b, h)
{
	return b * h * 0.5;
}
function areTheyClose(x,y)
{
	if( x == y )
		return false;
	var d = Math.abs(x - y);
	var p = d/x;
	if( p > 0.2 )
		return false;
	else
		return true;
}
function mod(n, m)
{
      while (n >= m)
      {
            n = n-m;
      }
      return(n);
      /*Keeps subtracting the number you want to divide by until the remainder is less than the original divisor, and then returning the remainder.
      */
}
function round(number,decimalPlaces)
{
	if(decimalPlaces == undefined)
		decimalPlaces = 2;
	return Math.round(parseFloat(number) * Math.pow(10, decimalPlaces)) / Math.pow(10, decimalPlaces);
}

function simplify(n,d)
{
	if( n == 0 )
	{
		return "0";
	}
	//if the denom is negative, switch signs. We want -1/2 not 1/-2
	if( d < 0 )
	{
		d = -d;
		n = -n;
	}
	//reduce fractions starting from 31
	for(var i=31;i>1;i--)
	{
		if( n % i == 0 && d % i == 0 )
		{
			n = n/i;
			d = d/i;
		}
	}
	//if it's -1 or 1
	if( Math.abs(n) == d )
	{
		if( n > 0)
		{
			return "1";
		}
		else
		{
			return "-1";
		}
	}
	// if improper
	else if( Math.abs(n) > d )
	{
		var num = Math.abs(n) % d;
		var whole = n/d;
		if( num == 0 )
		{
			return whole;
		}
		else 
		{
			if( whole < 0)
			{
				whole = Math.ceil(whole);
			}
			else
			{
				whole = Math.floor(whole);				
			}
			//since the whole number takes the sign, we need only positives for the fraction
			n = Math.abs(num);
			return  whole + " " + formatFraction(n,d); 			
		}
	}
	//otherwise, it's a proper fraction, simply format and return
	else
	{
		return formatFraction(n,d); 
	}
}
function isRational(x)
{
	var y = x * 1000;
	if( Math.round(y) == y )
		return true;
	return false;
}
function generateFraction()
{
	var d = 0;
	var n = 0;
	while(d == n)
	{
		 d = random(9);
		 n = random(d-1);
	}
	var a = new Array(n,d);
	return a;
}
function adjustFraction(n,d)
{
	if(fifty())
		n += random(d);
	else
		n -= random(n-1);
	return formatFraction(n,d);
}
function formatFraction(n,d)
{
//	n = Math.round(n*10000)/10000;
//	d = Math.round(d*10000)/10000;	
	var string = "";
	if( n != 0)
	{
		string += ' <span class="fraction" >' + 
		'<span class="numerator">' + n + '</span>' +
		'<span class="denominator">'+ d + '</span>' +
		'</span>';
	}
	return string;
}

/*
* This script depends on no outside libraries.
*/
 
Inflector = {
/*
     * The order of all these lists has been reversed from the way 
     * ActiveSupport had them to keep the correct priority.
     */
    Inflections: {
        plural: [
            [/(quiz)$/i,               "$1zes"  ],
            [/(woman)$/i,               "women"  ],                        
            [/^(ox)$/i,                "$1en"   ],
            [/([m|l])ouse$/i,          "$1ice"  ],
            [/(matr|vert|ind)ix|ex$/i, "$1ices" ],
            [/(x|ch|ss|sh)$/i,         "$1es"   ],
            [/([^aeiouy]|qu)y$/i,      "$1ies"  ],
            [/(hive)$/i,               "$1s"    ],
            [/(?:([^f])fe|([lr])f)$/i, "$1$2ves"],
            [/sis$/i,                  "ses"    ],
            [/([ti])um$/i,             "$1a"    ],
            [/(buffal|tomat)o$/i,      "$1oes"  ],
            [/(bu)s$/i,                "$1ses"  ],
            [/(alias|status)$/i,       "$1es"   ],
            [/(octop|vir)us$/i,        "$1i"    ],
            [/(ax|test)is$/i,          "$1es"   ],
            [/s$/i,                    "s"      ],
            [/$/,                      "s"      ]
        ],
        singular: [
            [/(quiz)zes$/i,                                                    "$1"     ],
            [/(matr)ices$/i,                                                   "$1ix"   ],
            [/(vert|ind)ices$/i,                                               "$1ex"   ],
            [/^(ox)en/i,                                                       "$1"     ],
            [/(alias|status)es$/i,                                             "$1"     ],
            [/(octop|vir)i$/i,                                                 "$1us"   ],
            [/(cris|ax|test)es$/i,                                             "$1is"   ],
            [/(shoe)s$/i,                                                      "$1"     ],
            [/(o)es$/i,                                                        "$1"     ],
            [/(bus)es$/i,                                                      "$1"     ],
            [/([m|l])ice$/i,                                                   "$1ouse" ],
            [/(x|ch|ss|sh)es$/i,                                               "$1"     ],
            [/(m)ovies$/i,                                                     "$1ovie" ],
            [/(s)eries$/i,                                                     "$1eries"],
            [/([^aeiouy]|qu)ies$/i,                                            "$1y"    ],
            [/([lr])ves$/i,                                                    "$1f"    ],
            [/(tive)s$/i,                                                      "$1"     ],
            [/(hive)s$/i,                                                      "$1"     ],
            [/([^f])ves$/i,                                                    "$1fe"   ],
            [/(^analy)ses$/i,                                                  "$1sis"  ],
            [/((a)naly|(b)a|(d)iagno|(p)arenthe|(p)rogno|(s)ynop|(t)he)ses$/i, "$1$2sis"],
            [/([ti])a$/i,                                                      "$1um"   ],
            [/(n)ews$/i,                                                       "$1ews"  ],
            [/s$/i,                                                            ""       ]
        ],
        irregular: [
            ['move',   'moves'   ],
            ['sex',    'sexes'   ],
            ['child',  'children'],
            ['man',    'men'     ],
	        ['woman',  'women'   ],            
            ['person', 'people'  ]
        ],
        uncountable: [
            "sheep",
            "fish",
            "series",
            "species",
            "money",
            "rice",
            "information",
            "equipment",
			"beef"
        ]
    },
    ordinalize: function(number) {
        if (11 <= parseInt(number) % 100 && parseInt(number) % 100 <= 13) {
            return number + "th";
        } else {
            switch (parseInt(number) % 10) {
                case  1: return number + "st";
                case  2: return number + "nd";
                case  3: return number + "rd";
                default: return number + "th";
            }
        }
    },
    pluralize: function(word) {
        for (var i = 0; i < Inflector.Inflections.uncountable.length; i++) {
            var uncountable = Inflector.Inflections.uncountable[i];
            if( word.noun == undefined )
            {
               if (word.toLowerCase() == uncountable) 
	           {
	                return uncountable;
	           }	
            }
            else
            {
	            if (word.noun.toLowerCase() == uncountable) 
	            {
	                return uncountable;
	            }
            }
        }
        for (var i = 0; i < Inflector.Inflections.irregular.length; i++) {
            var singular = Inflector.Inflections.irregular[i][0];
            var plural   = Inflector.Inflections.irregular[i][1];
            if( word.noun == undefined )
            {
            	if ((word.toLowerCase() == singular) || (word == plural)) {
	                return plural;
	            }
            } else {            
	            if ((word.noun.toLowerCase() == singular) || (word.noun == plural)) {
	                return plural;
	            }
            }
        }
        for (var i = 0; i < Inflector.Inflections.plural.length; i++) {
            var regex          = Inflector.Inflections.plural[i][0];
            var replace_string = Inflector.Inflections.plural[i][1];
            if (regex.test(word)) 
            {
            	if( word.noun == undefined )
            		return word.replace(regex, replace_string);
            	else
                	return word.noun.replace(regex, replace_string);
            }
        }
		return "";
    }
};
 
function ordinalize(number) {
    return Inflector.ordinalize(number);
}
 
/*
 * Javascript doesnt have optional parameters or overloading so I had to use
 * the ever popular pseudo options hash object technique.
 * required properties:
 *     count    Number of objects to pluralize
 *     singular Singular noun for the objects
 * optional property:
 *     plural   Plural (probably irregular) noun for the objects
 * examples:
 *      pluralize({ count: total_count, singular: "Issue" })
 *      pluralize({ count: total_count, singular: "Goose", plural: "Geese" })
 */
function pluralize(options) {
    return " " + (1 == parseInt(options.count) ?
        options.singular :
        options.plural || Inflector.pluralize(options.singular));
}
