/*
  PFrameworkCS API
  
  Copyright (C) 2005 by Jernej Kos <kostko@jweb-network.net>
  Copyright (C) 2005 by Unimatrix-One (www.unimatrix-one.org)
  
  This javascript is part of the PFramework CMS system. Any unauthorised
  use outside of this system is strictly prohibited.
*/

// escape a character

function escapeJSONChar(c)
{
    if(c == "\"" || c == "\\") return "\\" + c;
    else if (c == "\b") return "\\b";
    else if (c == "\f") return "\\f";
    else if (c == "\n") return "\\n";
    else if (c == "\r") return "\\r";
    else if (c == "\t") return "\\t";
    var hex = c.charCodeAt(0).toString(16);
    if(hex.length == 1) return "\\u000" + hex;
    else if(hex.length == 2) return "\\u00" + hex;
    else if(hex.length == 3) return "\\u0" + hex;
    else return "\\u" + hex;
}


// encode a string into JSON format

function escapeJSONString(s)
{
    // The following should suffice but Safari's regex is b0rken
    // (doesn't support callback substitutions)
    //
    //   return "\"" + s.replace(/([^\u0020-\u007f]|[\\\"])/g,
    //                           escapeJSONChar) + "\"";

    // Rather inefficient way to do it
    var parts = s.split("");
    for(var i=0; i < parts.length; i++) {
  var c =parts[i];
  if(c == '"' ||
     c == '\\' ||
     c.charCodeAt(0) < 32 ||
     c.charCodeAt(0) >= 128)
      parts[i] = escapeJSONChar(parts[i]);
    }
    return "\"" + parts.join("") + "\"";
}


// Marshall objects to JSON format

function toJSON(o)
{
    if(o == null) {
  return "null";
    } else if(o.constructor == String) {
  return escapeJSONString(o);
    } else if(o.constructor == Number) {
  return o.toString();
    } else if(o.constructor == Boolean) {
  return o.toString();
    } else if(o.constructor == Date) {
      return '{javaClass: "java.util.Date", time: ' + o.valueOf()/1000 +'}';
  //return o.valueOf().toString();
    } else if(o.constructor == Array) {
  var v = [];
  for(var i = 0; i < o.length; i++) v.push(toJSON(o[i]));
  return "[" + v.join(", ") + "]";
    } else {
  var v = [];
  for(attr in o) {
      if(o[attr] == null) v.push("\"" + attr + "\": null");
      else if(typeof o[attr] == "function"); // skip
      else v.push(escapeJSONString(attr) + ": " + toJSON(o[attr]));
  }
  return "{" + v.join(", ") + "}";
    }
}