use :node;

var Node = module.require('../Node').Node;

fn StringLiteral(chars, column)

extends Node {

this.type = 'StringLiteral';
this.chars = chars;
this.column = column;

}

StringLiteral.prototype.codegen = () -> {

if !super.codegen() {
  return;
}

var elements = [];

for value in this.chars {
  var lastElement;

  if typeof value == 'string' {
    lastElement = elements[elements.length - 1];
    if lastElement?.type == 'Literal' {
      lastElement.value += value;
    } else {
      elements.push({
        type: 'Literal',
        value: value
      });
    }
  } else if value?.type == "StringLiteralNewLine" {
    lastElement = elements[elements.length - 1];
    if lastElement?.type == 'Literal' {
      lastElement.value += value.toString(this.column - 1);
    } else {
      elements.push({
        type: 'Literal',
        value: value.toString(this.column - 1)
      });
    }
  } else {
    value.parent = this;
    elements.push(value.codegen());
  }
}

if elements.length == 0 {
  return {
    "type": "Literal",
    "value": ""
  };
} else if elements.length == 1 {
  return elements[0];
}

var reduced = elements.reduce((left, right) -> {
  return {
    type: 'BinaryExpression',
    operator: '+',
    left: left,
    right: right
  };
});

this.type = reduced.type;
this.operator = reduced.operator;
this.left = reduced.left;
this.right = reduced.right;

return this;

};

StringLiteral.prototype.hasCallExpression = () -> false;

StringLiteral.NewLine = fn (text) {

this.type = "StringLiteralNewLine";

this.toString = (column) -> {
      var t = text.replace(/\r\n/g, '').replace(/\t/g, '    ');

  if t.length < column {
    return '';
  }

  return t.substring(column);
};

};

exports.StringLiteral = StringLiteral;