JsPlate.js 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109
  1. /**
  2. @constructor
  3. */
  4. JSDOC.JsPlate = function(templateFile) {
  5. if (templateFile) this.template = IO.readFile(templateFile);
  6. this.templateFile = templateFile;
  7. this.code = "";
  8. this.parse();
  9. }
  10. JSDOC.JsPlate.prototype.parse = function() {
  11. this.template = this.template.replace(/\{#[\s\S]+?#\}/gi, "");
  12. this.code = "var output=\u001e"+this.template;
  13. this.code = this.code.replace(
  14. /<for +each="(.+?)" +in="(.+?)" *>/gi,
  15. function (match, eachName, inName) {
  16. return "\u001e;\rvar $"+eachName+"_keys = keys("+inName+");\rfor(var $"+eachName+"_i = 0; $"+eachName+"_i < $"+eachName+"_keys.length; $"+eachName+"_i++) {\rvar $"+eachName+"_last = ($"+eachName+"_i == $"+eachName+"_keys.length-1);\rvar $"+eachName+"_key = $"+eachName+"_keys[$"+eachName+"_i];\rvar "+eachName+" = "+inName+"[$"+eachName+"_key];\routput+=\u001e";
  17. }
  18. );
  19. this.code = this.code.replace(/<if test="(.+?)">/g, "\u001e;\rif ($1) { output+=\u001e");
  20. this.code = this.code.replace(/<elseif test="(.+?)"\s*\/>/g, "\u001e;}\relse if ($1) { output+=\u001e");
  21. this.code = this.code.replace(/<else\s*\/>/g, "\u001e;}\relse { output+=\u001e");
  22. this.code = this.code.replace(/<\/(if|for)>/g, "\u001e;\r};\routput+=\u001e");
  23. this.code = this.code.replace(
  24. /\{\+\s*([\s\S]+?)\s*\+\}/gi,
  25. function (match, code) {
  26. code = code.replace(/"/g, "\u001e"); // prevent qoute-escaping of inline code
  27. code = code.replace(/(\r?\n)/g, " ");
  28. return "\u001e+ ("+code+") +\u001e";
  29. }
  30. );
  31. this.code = this.code.replace(
  32. /\{!\s*([\s\S]+?)\s*!\}/gi,
  33. function (match, code) {
  34. code = code.replace(/"/g, "\u001e"); // prevent qoute-escaping of inline code
  35. code = code.replace(/(\n)/g, " ");
  36. return "\u001e; "+code+";\routput+=\u001e";
  37. }
  38. );
  39. this.code = this.code+"\u001e;";
  40. this.code = this.code.replace(/(\r?\n)/g, "\\n");
  41. this.code = this.code.replace(/"/g, "\\\"");
  42. this.code = this.code.replace(/\u001e/g, "\"");
  43. }
  44. JSDOC.JsPlate.prototype.toCode = function() {
  45. return this.code;
  46. }
  47. JSDOC.JsPlate.keys = function(obj) {
  48. var keys = [];
  49. if (obj.constructor.toString().indexOf("Array") > -1) {
  50. for (var i = 0; i < obj.length; i++) {
  51. keys.push(i);
  52. }
  53. }
  54. else {
  55. for (var i in obj) {
  56. keys.push(i);
  57. }
  58. }
  59. return keys;
  60. };
  61. JSDOC.JsPlate.values = function(obj) {
  62. var values = [];
  63. if (obj.constructor.toString().indexOf("Array") > -1) {
  64. for (var i = 0; i < obj.length; i++) {
  65. values.push(obj[i]);
  66. }
  67. }
  68. else {
  69. for (var i in obj) {
  70. values.push(obj[i]);
  71. }
  72. }
  73. return values;
  74. };
  75. JSDOC.JsPlate.prototype.process = function(data, compact) {
  76. var keys = JSDOC.JsPlate.keys;
  77. var values = JSDOC.JsPlate.values;
  78. try {
  79. eval(this.code);
  80. }
  81. catch (e) {
  82. print(">> There was an error evaluating the compiled code from template: "+this.templateFile);
  83. print(" The error was on line "+e.lineNumber+" "+e.name+": "+e.message);
  84. var lines = this.code.split("\r");
  85. if (e.lineNumber-2 >= 0) print("line "+(e.lineNumber-1)+": "+lines[e.lineNumber-2]);
  86. print("line "+e.lineNumber+": "+lines[e.lineNumber-1]);
  87. print("");
  88. }
  89. if (compact) { // patch by mcbain.asm
  90. // Remove lines that contain only space-characters, usually left by lines in the template
  91. // which originally only contained JSPlate tags or code. This makes it easier to write
  92. // non-tricky templates which still put out nice code (not bloated with extra lines).
  93. // Lines purposely left blank (just a line ending) are left alone.
  94. output = output.replace(/\s+?(\r?)\n/g, "$1\n");
  95. }
  96. /*debug*///print(this.code);
  97. return output;
  98. }