00001
00002 (function() {
00003 var XMLAttribute, XMLElement, XMLNode, XMLProcessingInstruction, create, every, isFunction, isObject,
00004 extend = function(child, parent) { for (var key in parent) { if (hasProp.call(parent, key)) child[key] = parent[key]; } function ctor() { this.constructor = child; } ctor.prototype = parent.prototype; child.prototype = new ctor(); child.__super__ = parent.prototype; return child; },
00005 hasProp = {}.hasOwnProperty;
00006
00007 create = require('lodash/create');
00008
00009 isObject = require('lodash/isObject');
00010
00011 isFunction = require('lodash/isFunction');
00012
00013 every = require('lodash/every');
00014
00015 XMLNode = require('./XMLNode');
00016
00017 XMLAttribute = require('./XMLAttribute');
00018
00019 XMLProcessingInstruction = require('./XMLProcessingInstruction');
00020
00021 module.exports = XMLElement = (function(superClass) {
00022 extend(XMLElement, superClass);
00023
00024 function XMLElement(parent, name, attributes) {
00025 XMLElement.__super__.constructor.call(this, parent);
00026 if (name == null) {
00027 throw new Error("Missing element name");
00028 }
00029 this.name = this.stringify.eleName(name);
00030 this.children = [];
00031 this.instructions = [];
00032 this.attributes = {};
00033 if (attributes != null) {
00034 this.attribute(attributes);
00035 }
00036 }
00037
00038 XMLElement.prototype.clone = function() {
00039 var att, attName, clonedSelf, i, len, pi, ref, ref1;
00040 clonedSelf = create(XMLElement.prototype, this);
00041 if (clonedSelf.isRoot) {
00042 clonedSelf.documentObject = null;
00043 }
00044 clonedSelf.attributes = {};
00045 ref = this.attributes;
00046 for (attName in ref) {
00047 if (!hasProp.call(ref, attName)) continue;
00048 att = ref[attName];
00049 clonedSelf.attributes[attName] = att.clone();
00050 }
00051 clonedSelf.instructions = [];
00052 ref1 = this.instructions;
00053 for (i = 0, len = ref1.length; i < len; i++) {
00054 pi = ref1[i];
00055 clonedSelf.instructions.push(pi.clone());
00056 }
00057 clonedSelf.children = [];
00058 this.children.forEach(function(child) {
00059 var clonedChild;
00060 clonedChild = child.clone();
00061 clonedChild.parent = clonedSelf;
00062 return clonedSelf.children.push(clonedChild);
00063 });
00064 return clonedSelf;
00065 };
00066
00067 XMLElement.prototype.attribute = function(name, value) {
00068 var attName, attValue;
00069 if (name != null) {
00070 name = name.valueOf();
00071 }
00072 if (isObject(name)) {
00073 for (attName in name) {
00074 if (!hasProp.call(name, attName)) continue;
00075 attValue = name[attName];
00076 this.attribute(attName, attValue);
00077 }
00078 } else {
00079 if (isFunction(value)) {
00080 value = value.apply();
00081 }
00082 if (!this.options.skipNullAttributes || (value != null)) {
00083 this.attributes[name] = new XMLAttribute(this, name, value);
00084 }
00085 }
00086 return this;
00087 };
00088
00089 XMLElement.prototype.removeAttribute = function(name) {
00090 var attName, i, len;
00091 if (name == null) {
00092 throw new Error("Missing attribute name");
00093 }
00094 name = name.valueOf();
00095 if (Array.isArray(name)) {
00096 for (i = 0, len = name.length; i < len; i++) {
00097 attName = name[i];
00098 delete this.attributes[attName];
00099 }
00100 } else {
00101 delete this.attributes[name];
00102 }
00103 return this;
00104 };
00105
00106 XMLElement.prototype.instruction = function(target, value) {
00107 var i, insTarget, insValue, instruction, len;
00108 if (target != null) {
00109 target = target.valueOf();
00110 }
00111 if (value != null) {
00112 value = value.valueOf();
00113 }
00114 if (Array.isArray(target)) {
00115 for (i = 0, len = target.length; i < len; i++) {
00116 insTarget = target[i];
00117 this.instruction(insTarget);
00118 }
00119 } else if (isObject(target)) {
00120 for (insTarget in target) {
00121 if (!hasProp.call(target, insTarget)) continue;
00122 insValue = target[insTarget];
00123 this.instruction(insTarget, insValue);
00124 }
00125 } else {
00126 if (isFunction(value)) {
00127 value = value.apply();
00128 }
00129 instruction = new XMLProcessingInstruction(this, target, value);
00130 this.instructions.push(instruction);
00131 }
00132 return this;
00133 };
00134
00135 XMLElement.prototype.toString = function(options, level) {
00136 var att, child, i, indent, instruction, j, len, len1, name, newline, offset, pretty, r, ref, ref1, ref2, ref3, ref4, ref5, space;
00137 pretty = (options != null ? options.pretty : void 0) || false;
00138 indent = (ref = options != null ? options.indent : void 0) != null ? ref : ' ';
00139 offset = (ref1 = options != null ? options.offset : void 0) != null ? ref1 : 0;
00140 newline = (ref2 = options != null ? options.newline : void 0) != null ? ref2 : '\n';
00141 level || (level = 0);
00142 space = new Array(level + offset + 1).join(indent);
00143 r = '';
00144 ref3 = this.instructions;
00145 for (i = 0, len = ref3.length; i < len; i++) {
00146 instruction = ref3[i];
00147 r += instruction.toString(options, level);
00148 }
00149 if (pretty) {
00150 r += space;
00151 }
00152 r += '<' + this.name;
00153 ref4 = this.attributes;
00154 for (name in ref4) {
00155 if (!hasProp.call(ref4, name)) continue;
00156 att = ref4[name];
00157 r += att.toString(options);
00158 }
00159 if (this.children.length === 0 || every(this.children, function(e) {
00160 return e.value === '';
00161 })) {
00162 r += '/>';
00163 if (pretty) {
00164 r += newline;
00165 }
00166 } else if (pretty && this.children.length === 1 && (this.children[0].value != null)) {
00167 r += '>';
00168 r += this.children[0].value;
00169 r += '</' + this.name + '>';
00170 r += newline;
00171 } else {
00172 r += '>';
00173 if (pretty) {
00174 r += newline;
00175 }
00176 ref5 = this.children;
00177 for (j = 0, len1 = ref5.length; j < len1; j++) {
00178 child = ref5[j];
00179 r += child.toString(options, level + 1);
00180 }
00181 if (pretty) {
00182 r += space;
00183 }
00184 r += '</' + this.name + '>';
00185 if (pretty) {
00186 r += newline;
00187 }
00188 }
00189 return r;
00190 };
00191
00192 XMLElement.prototype.att = function(name, value) {
00193 return this.attribute(name, value);
00194 };
00195
00196 XMLElement.prototype.ins = function(target, value) {
00197 return this.instruction(target, value);
00198 };
00199
00200 XMLElement.prototype.a = function(name, value) {
00201 return this.attribute(name, value);
00202 };
00203
00204 XMLElement.prototype.i = function(target, value) {
00205 return this.instruction(target, value);
00206 };
00207
00208 return XMLElement;
00209
00210 })(XMLNode);
00211
00212 }).call(this);