import { RelationLineType, RelationType } from "@/enum";
import { ColumnRelation, ProjectInfo, RemarkInfo, TableItemType, TopicAreaInfo } from "@/type";
import { Graph } from "@antv/x6";

const dasharrayMap = {
  // [RelationLineType.Dashdot]: "5 5,1 5",
  [RelationLineType.Dash]: "5,5",
  [RelationLineType.Solid]: "0",
  [RelationLineType.Dotted]: "1,5",
}
export const render = (graph: Graph, project: ProjectInfo) => {
  const { tables, relations, topicAreas, remarkInfos } = project;
  // 渲染表格
  const renderTable = (tableItem: TableItemType) => {
    const node = graph.addNode({
      shape: "table-node",
      x: tableItem.table.style?.x || 100,
      y: tableItem.table.style?.y || 100,
      width: project.setting.tableWidth,
      height: 69,
      id: tableItem.table.id,
      data: tableItem,
      zIndex: 3,
      ports: {
        groups: {
          // 字段名前连接桩
          columnPort: {
            markup: [
              {
                tagName: "rect",
                selector: "rect",
              },
              {
                tagName: "circle",
                selector: "circle",
              },
            ],
            position: {
              name: "absolute",
              args: {
                x: 12,
                y: 42,
              },
            },
          },
        },
      },
    });
    console.log(node)
  };
  // 渲染主题区域
  const renderTopicArea = (topicArea: TopicAreaInfo) => {
    graph.addNode({
      shape: "topic-node",
      x: topicArea.style?.x || 100,
      y: topicArea.style?.y || 100,
      width: topicArea.style?.width || 200,
      height: topicArea.style?.height || 200,
      id: topicArea.id,
      data: topicArea,
      zIndex: 0,
    });
  };
  // 渲染备注
  const renderRemark = (remark: RemarkInfo) => {
    graph?.addNode({
      shape: "notice-node",
      x: remark.style?.x || 100,
      y: remark.style?.y || 100,
      width: remark.style?.width || 200,
      height: remark.style?.height || 200,
      id: remark.id,
      data: remark,
      zIndex: 1,
    });
  };
  // 渲染关系
  const renderRelationEdge = (relation: ColumnRelation) => {
    // 添加关系连线
    const relationEdge = graph?.addEdge({
      id: relation.id,
      zIndex: 0,
      router: {
        name: "er",
        args: {
          offset: "center",
          direction: "H",
        },
      },
      connector: { name: "rounded" },
      attrs: {
        line: {
          stroke: relation.style?.color || "#333",
          strokeWidth: relation.style?.width || 1,
          targetMarker: null,
          strokeDasharray: dasharrayMap[relation.style?.lineType as RelationLineType || RelationLineType.Solid]
        },
      },
      source: {
        cell: relation.primaryTable,
        port: relation.primaryKey + "_port2",
        anchor: "left",
      },
      target: {
        cell: relation.foreignTable,
        port: relation.foreignKey + "_port2",
        anchor: "left",
      },
      data: {
        type: "relation",
      },
      defaultLabel: {
        markup: [
          {
            tagName: "circle",
            selector: "bg",
          },
          {
            tagName: "text",
            selector: "txt",
          },
        ],
        attrs: {
          txt: {
            fill: "#fff",
            textAnchor: "middle",
            textVerticalAnchor: "middle",
          },
          bg: {
            ref: "txt",
            fill: "#333",
            r: 10,
            strokeWidth: 0,
          },
        },
      },
    });

    if (project.setting.showRelation) {
      relationEdge?.appendLabel({
        attrs: {
          txt: {
            text: relation.relationType === RelationType.OneToOne ||
            relation.relationType === RelationType.OneToMany
              ? "1"
              : "n",
          },
          bg: {
            fill: relation.style?.color || "#333",
          }
        },
        position: {
          distance: 25,
        },
      });
      relationEdge?.appendLabel({
        attrs: {
          txt: {
            text: relation.relationType === RelationType.OneToMany
              ? "n"
              : "1",
          },
          bg: {
            fill: relation.style?.color || "#333",
          }
        },
        position: {
          distance: -25,
        },
      });
    }
  };

  const cells = graph.getCells();

  const allIds = [
    ...tables.map((table) => table.table.id),
    ...topicAreas.map((topicArea) => topicArea.id),
    ...remarkInfos.map((remark) => remark.id),
    ...relations.map((relation) => relation.id),
  ];
  // 移除空数据节点
  cells.forEach((cell) => {
    if (!allIds.includes(cell.id)) {
      cell.remove();
    }
  });
  tables.forEach((tableItem) => {
    if (!graph.getCellById(tableItem.table.id)) {
      renderTable(tableItem);
    } else {
      const cell = graph.getCellById(tableItem.table.id);
      if (cell?.isNode()) {
        cell.size(project.setting.tableWidth, cell.size().height);
        cell.setPosition(tableItem.table.style?.x, tableItem.table.style?.y);
        cell.setData(tableItem);
      }
    }
  });
  topicAreas.forEach((topicArea) => {
    if (!graph.getCellById(topicArea.id)) {
      renderTopicArea(topicArea);
    } else {
      const cell = graph.getCellById(topicArea.id);
      if (cell?.isNode()) {
        cell.setData(topicArea);
        cell.setPosition(topicArea.style?.x, topicArea.style?.y);
        cell.setSize(topicArea.style?.width, topicArea.style?.height);
      }
    }
  });
  remarkInfos.forEach((remark) => {
    if (!graph.getCellById(remark.id)) {
      renderRemark(remark);
    } else {
      const cell = graph.getCellById(remark.id);
      if (cell?.isNode()) {
        cell.setData(remark);
        cell.setPosition(remark.style?.x, remark.style?.y);
        cell.setSize(remark.style?.width, remark.style?.height);
      }
    }
  });
  relations.forEach((relation) => {
    const relationEdge = graph.getCellById(relation.id);

    if (!relationEdge) {
      renderRelationEdge(relation);
    } else if(relationEdge.isEdge()) {
      if (project.setting.showRelation) {
        // 更新标签
        relationEdge.setLabelAt(0, {
          attrs: {
            txt: {
              text:
                relation.relationType === RelationType.OneToOne ||
                relation.relationType === RelationType.OneToMany
                  ? "1"
                  : "n",
            },
            bg: {
              fill: relation.style?.color || "#333",
            }
          },
          position: {
            distance: 25,
          },
        });
        relationEdge.setLabelAt(1, {
          attrs: {
            txt: {
              text:
                relation.relationType === RelationType.OneToMany
                  ? "n"
                  : "1",
            },
            bg: {
              fill: relation.style?.color || "#333",
            }
          },
          position: {
            distance: -25,
          },
        });
      } else {
        relationEdge.setLabels([]);
      }
      relationEdge.setAttrs({
        line: {
          stroke: relation.style?.color || "#333",
          strokeWidth: relation.style?.width || 1,
          strokeDasharray: dasharrayMap[relation.style?.lineType as RelationLineType || RelationLineType.Solid]
        },
      });
    }
  });
};
