/*
 * Copyright (C) Sapphirecode - All Rights Reserved
 * This file is part of graphviz-builder which is released under MIT.
 * See file 'LICENSE' for full license details.
 * Created by Timo Hocker <timo@scode.ovh>, May 2020
 */

import { NodeStyles } from '../enums/Styles';
import { Element } from './Element';
import { Color } from './Color';

export class Node extends Element {
  public label?: string;
  public is_table = false;
  public table_contents?: Array<Array<string>>;
  public style?: NodeStyles;
  public color?: Color;

  public constructor (name: string, parent: string, label?: string) {
    super (name, parent);
    this.label = label;
  }

  private get serialized_table (): string {
    if (typeof this.table_contents === 'undefined')
      throw new Error ('table contents are undefined');

    const mapped_columns = this.table_contents
      .map ((val) => `<td>${val.join ('</td><td>')}</td>`);

    return `<table>\n  <tr>${
      mapped_columns.join ('</tr>\n  <tr>')
    }</tr>\n</table>`;
  }

  // eslint-disable-next-line @typescript-eslint/naming-convention
  public toString (): string {
    const attributes = [];

    if (this.label || this.is_table) {
      attributes.push ({
        name:  'label',
        value: this.is_table
          ? this.serialized_table
          : this.label
      });
    }
    if (this.style)
      attributes.push ({ name: 'style', value: this.style.toString () });
    if (this.color)
      attributes.push ({ name: 'color', value: this.color.toString () });

    const attrs = attributes.map ((v) => {
      const d = (/\n/u).test (v.value as string)
        ? [
          '<',
          '>'
        ]
        : [
          '"',
          '"'
        ];

      return `${v.name}=${d[0]}${v.value}${d[1]}`;
    })
      .join (', ');

    if (attributes.length > 0)
      return `${this.full_name} [${attrs}]`;

    return `${this.full_name}`;
  }
}