/* eslint-disable */
const ANCHOR_TYPE = {
  main: "main",
  middle: "middle",
  first: "first",
  last: "last"
};

function Anchor(uuid, type, x, y) {
  this.uuid = null;
  this.x = 0;
  this.y = 0;
  this.type = ANCHOR_TYPE.main;
  this.isFirst = false;
  this.isLast = false;
  this.ndex = 0;
  this.typeIndex = 0;
  this.uuid = uuid;
  this.x = x;
  this.y = y;
  this.type = (type === ANCHOR_TYPE.middle) ? ANCHOR_TYPE.middle : ANCHOR_TYPE.main;
}

function Polyline(uuid, points, strokeWidth, rebuildPath) {

  this.id = null;
  this.points = [];
  this.path = [];
  this.anchors = [];
  this.strokeWidth = 1;
  this.radius = 15;
  this.showDetails = false;
  this.element = null;
  this.isDefaultConditionAvailable = false;
  this.closePath = false;
  /* Array on coordinates:
   * points: [{x: 410, y: 110}, 1
   *			{x: 570, y: 110}, 1 2
   *			{x: 620, y: 240},   2 3
   *			{x: 750, y: 270},     3 4
   *			{x: 650, y: 370}];      4
   */
  this.points = points;
  this.rebuildPath = rebuildPath;

  /*
   * path for graph
   * [["M", x1, y1], ["L", x2, y2], ["C", ax, ay, bx, by, x3, y3], ["L", x3, y3]]
   */
  this.path = [];

  this.anchors = [];

  if (strokeWidth) this.strokeWidth = strokeWidth;

  this.closePath = false;

  this.getLinesCount = function () {
    return this.points.length - 1;
  };

  this.normalizeCoordinates = function () {
    for (let i = 0; i < this.points.length; i++) {
      this.points[i].x = parseFloat(this.points[i].x);
      this.points[i].y = parseFloat(this.points[i].y);
    }
  };

  this.getAnchorsCount = function (type) {
    if (!type)
      return this.anchors.length;
    else {
      let count = 0;
      for (let i = 0; i < this.getAnchorsCount(); i++) {
        const anchor = this.anchors[i];
        if (anchor.getType() === type) {
          count++;
        }
      }
      return count;
    }
  };

  this.pushAnchor = function (type, x, y, index) {
    if (type === ANCHOR_TYPE.first) {
      index = 0;
      this.typeIndex = 0;
    } else if (type === ANCHOR_TYPE.last) {
      index = this.getAnchorsCount();
      this.typeIndex = 0;
    } else if (!index) {
      index = this.anchors.length;
    } else {
      for (let i = 0; i < this.getAnchorsCount(); i++) {
        const anchor = this.anchors[i];
        if (anchor.index > index) {
          anchor.index++;
          anchor.typeIndex++;
        }
      }
    }

    const anchor = new Anchor(this.id, ANCHOR_TYPE.main, x, y, index, this.typeIndex);

    this.anchors.push(anchor);
  };

  this._getLine = function (i) {
    return {x1: this.points[i].x, y1: this.points[i].y, x2: this.points[i + 1].x, y2: this.points[i + 1].y};
  };

  this.getLineAngle = function (i) {
    const line = this._getLine(i);
    return Math.atan2(line.y2 - line.y1, line.x2 - line.x1);
  };

  this.getLine = function (i) {
    const line = this._getLine(i);
    line.angle = this.getLineAngle(i);
    return line;
  };

  this.getAnchor = function (position) {
    return this.anchors[position];
  };

  this.getLineLength = function (i) {
    const line = this.getLine(i);
    return Math.sqrt(Math.pow(this.getLineLengthX(i), 2) + Math.pow(this.getLineLengthY(i), 2));
  };

  this.getLineLengthX = function (i) {
    const line = this.getLine(i);
    return (line.x2 - line.x1);
  };

  this.getLineLengthY = function (i) {
    const line = this.getLine(i);
    return (line.y2 - line.y1);
  },

  this.init = function (points) {
    const linesCount = this.getLinesCount();
    if (linesCount < 1)
      return;

    this.normalizeCoordinates();

    // create anchors

    this.pushAnchor(ANCHOR_TYPE.first, this.getLine(0).x1, this.getLine(0).y1);

    for (let i = 1; i < linesCount; i++) {
      const line1 = this.getLine(i - 1),
        line2 = this.getLine(i);

      //this.pushAnchor(ANCHOR_TYPE.middle, line1.x1 + line1.x2-line1.x1, line1.y1 + line1.y2-line1.y1);
      this.pushAnchor(ANCHOR_TYPE.main, line1.x2, line1.y2);
      //this.pushAnchor(ANCHOR_TYPE.middle,  line2.x1 + line2.x2-line2.x1, line2.y1 + line2.y2-line2.y1);
    }

    this.pushAnchor(ANCHOR_TYPE.last, this.getLine(linesCount - 1).x2, this.getLine(linesCount - 1).y2);
    this.rebuildPath(this);
  };

  this.init();

  this.getAnchors = function () {
    return this.anchors;
  };

  this.getAnchorByType = function (type, position) {
    if (type === ANCHOR_TYPE.first)
      return this.anchors[0];
    if (type === ANCHOR_TYPE.last)
      return this.anchors[this.getAnchorsCount() - 1];

    for (let i = 0; i < this.getAnchorsCount(); i++) {
      const anchor = this.anchors[i];
      if (anchor.type === type) {
        if (position === anchor.position)
          return anchor;
      }
    }
    return null;
  };

  this.addNewPoint = function (position, x, y) {
    //
    for (let i = 0; i < this.getLinesCount(); i++) {
      const line = this.getLine(i);
      if (x > line.x1 && x < line.x2 && y > line.y1 && y < line.y2) {
        this.points.splice(i + 1, 0, {x: x, y: y});
        break;
      }
    }
    this.rebuildPath(this);
  };

  this.transform = function (transformation) {
    this.element.transform(transformation);
  };

  this.attr = function (attrs) {
    this.element.attr(attrs);
  }
}

function Polygone(points, strokeWidth) {
  /* Array on coordinates:
   * points: [{x: 410, y: 110}, 1
   *			{x: 570, y: 110}, 1 2
   *			{x: 620, y: 240},   2 3
   *			{x: 750, y: 270},     3 4
   *			{x: 650, y: 370}];      4
   */
  this.points = points;

  /*
   * path for graph
   * [["M", x1, y1], ["L", x2, y2], ["C", ax, ay, bx, by, x3, y3], ["L", x3, y3]]
   */
  this.path = [];

  this.anchors = [];

  if (strokeWidth) this.strokeWidth = strokeWidth;

  this.closePath = true;
  this.init();
};


/*
 * Poligone is inherited from Poliline: draws closedPath of polyline
 */

/*var Foo = function () {
};
Foo.prototype = Polyline.prototype;

Polygone.prototype = new Foo();

Polygone.prototype.rebuildPath = function () {
  var path = [];
  //console.log("Polygone rebuildPath");
  for (var i = 0; i < this.getAnchorsCount(); i++) {
    var anchor = this.getAnchor(i);

    var pathType = ""
    if (i == 0)
      pathType = "M";
    else
      pathType = "L";

    var targetX = anchor.x, targetY = anchor.y;

    // anti smoothing
    if (this.strokeWidth % 2 == 1) {
      targetX += 0.5;
      targetY += 0.5;
    }

    path.push([pathType, targetX, targetY]);
  }
  if (this.closePath)
    path.push(["Z"]);

  this.path = path;
};*/
/*
 Polygone.prototype.transform = function(transformation){
 this.element.transform(transformation);
 };
 */

export default Polyline;
