separate class for connections
This commit is contained in:
parent
bc449cd86a
commit
8e5fcbeefa
268
graph.js
268
graph.js
|
@ -9,20 +9,31 @@ class graph {
|
||||||
// Оболочка (instanceof HTMLElement)
|
// Оболочка (instanceof HTMLElement)
|
||||||
#shell = document.getElementById("graph");
|
#shell = document.getElementById("graph");
|
||||||
|
|
||||||
|
// Оболочка (instanceof HTMLElement)
|
||||||
get shell() {
|
get shell() {
|
||||||
return this.#shell;
|
return this.#shell;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Реестр узлов
|
// Реестр узлов
|
||||||
nodes = new Set();
|
#nodes = new Set();
|
||||||
|
|
||||||
|
// Реестр узлов
|
||||||
|
get nodes() {
|
||||||
|
return this.#nodes;
|
||||||
|
}
|
||||||
|
|
||||||
// Реестр соединений
|
// Реестр соединений
|
||||||
connections = new Set();
|
#connections = new Set();
|
||||||
|
|
||||||
|
// Реестр соединений
|
||||||
|
get connections() {
|
||||||
|
return this.#connections;
|
||||||
|
}
|
||||||
|
|
||||||
// Класс узла
|
// Класс узла
|
||||||
node = class node {
|
#node = class node {
|
||||||
// Реестр входящих соединений
|
// Реестр входящих соединений
|
||||||
#inputs = new Map();
|
#inputs = new Set();
|
||||||
|
|
||||||
// Реестр входящих соединений
|
// Реестр входящих соединений
|
||||||
get inputs() {
|
get inputs() {
|
||||||
|
@ -30,7 +41,7 @@ class graph {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Реестр исходящих соединений
|
// Реестр исходящих соединений
|
||||||
#outputs = new Map();
|
#outputs = new Set();
|
||||||
|
|
||||||
// Реестр исходящих соединений
|
// Реестр исходящих соединений
|
||||||
get outputs() {
|
get outputs() {
|
||||||
|
@ -81,18 +92,18 @@ class graph {
|
||||||
return this.#increase;
|
return this.#increase;
|
||||||
}
|
}
|
||||||
|
|
||||||
constructor(data, graph) {
|
constructor(operator, data) {
|
||||||
// Инициализация оболочки
|
// Инициализация оболочки
|
||||||
const article = document.createElement("article");
|
const article = document.createElement("article");
|
||||||
article.id = graph.nodes.size;
|
article.id = operator.nodes.size;
|
||||||
article.classList.add("node", "unselectable");
|
article.classList.add("node", "unselectable");
|
||||||
article.style.top =
|
article.style.top =
|
||||||
graph.shell.offsetHeight / 2 -
|
operator.shell.offsetHeight / 2 -
|
||||||
this.#diameter / 2 +
|
this.#diameter / 2 +
|
||||||
(0.5 - Math.random()) * 500 +
|
(0.5 - Math.random()) * 500 +
|
||||||
"px";
|
"px";
|
||||||
article.style.left =
|
article.style.left =
|
||||||
graph.shell.offsetWidth / 2 -
|
operator.shell.offsetWidth / 2 -
|
||||||
this.#diameter / 2 +
|
this.#diameter / 2 +
|
||||||
(0.5 - Math.random()) * 500 +
|
(0.5 - Math.random()) * 500 +
|
||||||
"px";
|
"px";
|
||||||
|
@ -112,10 +123,10 @@ class graph {
|
||||||
this.#element = article;
|
this.#element = article;
|
||||||
|
|
||||||
// Запись в свойство
|
// Запись в свойство
|
||||||
this.#operator = graph;
|
this.#operator = operator;
|
||||||
|
|
||||||
// Запись в документ
|
// Запись в документ
|
||||||
graph.shell.appendChild(article);
|
operator.shell.appendChild(article);
|
||||||
|
|
||||||
// Инициализация
|
// Инициализация
|
||||||
this.init();
|
this.init();
|
||||||
|
@ -147,9 +158,6 @@ class graph {
|
||||||
attributes: true,
|
attributes: true,
|
||||||
attributeOldValue: true
|
attributeOldValue: true
|
||||||
});
|
});
|
||||||
|
|
||||||
// this.style.left = x + 'px';
|
|
||||||
// this.style.top = y + 'px';
|
|
||||||
}
|
}
|
||||||
|
|
||||||
configure(attribute) {
|
configure(attribute) {
|
||||||
|
@ -200,45 +208,11 @@ class graph {
|
||||||
this.element.setAttribute("data-graph-x", x);
|
this.element.setAttribute("data-graph-x", x);
|
||||||
this.element.setAttribute("data-graph-y", y);
|
this.element.setAttribute("data-graph-y", y);
|
||||||
|
|
||||||
for (const [connection, target] of this.outputs) {
|
// Перемещение исходящих соединений до узла
|
||||||
// Перебор исходящих соединений
|
for (const connection of this.outputs) connection.move(this);
|
||||||
|
|
||||||
// Инициализация координат для линии
|
// Перемещение входящих соединений до узла
|
||||||
const x1 = parseInt(this.element.style.left);
|
for (const connection of this.inputs) connection.move(this);
|
||||||
const y1 = parseInt(this.element.style.top);
|
|
||||||
|
|
||||||
// Запись новой координаты по горизонтали
|
|
||||||
connection.children[0].setAttribute(
|
|
||||||
"x1",
|
|
||||||
(isNaN(x1) ? 0 : x1) + this.element.offsetWidth / 2
|
|
||||||
);
|
|
||||||
|
|
||||||
// Запись новой координаты по вертикали
|
|
||||||
connection.children[0].setAttribute(
|
|
||||||
"y1",
|
|
||||||
(isNaN(y1) ? 0 : y1) + this.element.offsetHeight / 2
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
for (const [connection, target] of this.inputs) {
|
|
||||||
// Перебор входящих соединений
|
|
||||||
|
|
||||||
// Инициализация координат для линии
|
|
||||||
const x2 = parseInt(this.element.style.left);
|
|
||||||
const y2 = parseInt(this.element.style.top);
|
|
||||||
|
|
||||||
// Запись новой координаты по горизонтали
|
|
||||||
connection.children[0].setAttribute(
|
|
||||||
"x2",
|
|
||||||
(isNaN(x2) ? 0 : x2) + this.element.offsetWidth / 2
|
|
||||||
);
|
|
||||||
|
|
||||||
// Запись новой координаты по вертикали
|
|
||||||
connection.children[0].setAttribute(
|
|
||||||
"y2",
|
|
||||||
(isNaN(y2) ? 0 : y2) + this.element.offsetHeight / 2
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Обработка столкновений
|
// Обработка столкновений
|
||||||
this.collision(this.operator.nodes);
|
this.collision(this.operator.nodes);
|
||||||
|
@ -309,6 +283,150 @@ class graph {
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// Класс узла
|
||||||
|
get node() {
|
||||||
|
return this.#node;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Класс соединения
|
||||||
|
#connection = class connection {
|
||||||
|
// HTML-элемент
|
||||||
|
#element;
|
||||||
|
|
||||||
|
// HTML-элемент
|
||||||
|
get element() {
|
||||||
|
return this.#element;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Инстанция node от которой начинается соединение
|
||||||
|
#from;
|
||||||
|
|
||||||
|
// Инстанция node от которой начинается соединение
|
||||||
|
get from() {
|
||||||
|
return this.#from;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Инстанция node на которой заканчивается соединение
|
||||||
|
#to;
|
||||||
|
|
||||||
|
// Инстанция node на которой заканчивается соединение
|
||||||
|
get to() {
|
||||||
|
return this.#to;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Оператор
|
||||||
|
#operator;
|
||||||
|
|
||||||
|
// Оператор
|
||||||
|
get operator() {
|
||||||
|
return this.#operator;
|
||||||
|
}
|
||||||
|
|
||||||
|
constructor(operator, from, to) {
|
||||||
|
// Запись свойства
|
||||||
|
this.#operator = operator;
|
||||||
|
|
||||||
|
// Запись свойства
|
||||||
|
this.#from = from;
|
||||||
|
|
||||||
|
// Запись свойства
|
||||||
|
this.#to = to;
|
||||||
|
|
||||||
|
// Инициализация оболочки
|
||||||
|
const svg = document.createElementNS("http://www.w3.org/2000/svg", "svg");
|
||||||
|
svg.id = operator.connections.size;
|
||||||
|
svg.classList.add("connection");
|
||||||
|
svg.setAttribute("data-from", from.element.id);
|
||||||
|
svg.setAttribute("data-to", to.element.id);
|
||||||
|
|
||||||
|
// Инициализация универсального буфера
|
||||||
|
let buffer;
|
||||||
|
|
||||||
|
// Инициализация оболочки
|
||||||
|
const line = document.createElementNS(
|
||||||
|
"http://www.w3.org/2000/svg",
|
||||||
|
"line"
|
||||||
|
);
|
||||||
|
line.setAttribute(
|
||||||
|
"x1",
|
||||||
|
(isNaN((buffer = parseInt(from.element.style.left))) ? 0 : buffer) +
|
||||||
|
from.element.offsetWidth / 2
|
||||||
|
);
|
||||||
|
line.setAttribute(
|
||||||
|
"y1",
|
||||||
|
(isNaN((buffer = parseInt(from.element.style.top))) ? 0 : buffer) +
|
||||||
|
from.element.offsetHeight / 2
|
||||||
|
);
|
||||||
|
line.setAttribute(
|
||||||
|
"x2",
|
||||||
|
(isNaN((buffer = parseInt(to.element.style.left))) ? 0 : buffer) +
|
||||||
|
to.element.offsetWidth / 2
|
||||||
|
);
|
||||||
|
line.setAttribute(
|
||||||
|
"y2",
|
||||||
|
(isNaN((buffer = parseInt(to.element.style.top))) ? 0 : buffer) +
|
||||||
|
to.element.offsetHeight / 2
|
||||||
|
);
|
||||||
|
line.setAttribute("stroke", "grey");
|
||||||
|
line.setAttribute("stroke-width", "8px");
|
||||||
|
|
||||||
|
// Запись свойства
|
||||||
|
this.#element = svg;
|
||||||
|
|
||||||
|
// Запись в оболочку
|
||||||
|
svg.append(line);
|
||||||
|
|
||||||
|
// Запись в документ
|
||||||
|
operator.shell.appendChild(svg);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Переместить
|
||||||
|
*
|
||||||
|
* @param {node} node Инстанция узла (связанного с соединением)
|
||||||
|
*/
|
||||||
|
move(node) {
|
||||||
|
// Инициализация названий аттрибутов
|
||||||
|
let x, y;
|
||||||
|
|
||||||
|
if (node === this.from) {
|
||||||
|
// Исходящее соединение
|
||||||
|
|
||||||
|
// Запись названий аттрибутов
|
||||||
|
x = "x1";
|
||||||
|
y = "y1";
|
||||||
|
} else if (node === this.to) {
|
||||||
|
// Входящее соединение
|
||||||
|
|
||||||
|
// Запись названий аттрибутов
|
||||||
|
x = "x2";
|
||||||
|
y = "y2";
|
||||||
|
} else return;
|
||||||
|
|
||||||
|
// Инициализация универсального буфера
|
||||||
|
let buffer;
|
||||||
|
|
||||||
|
// Запись отступа (координаты по горизонтали)
|
||||||
|
this.element.children[0].setAttribute(
|
||||||
|
x,
|
||||||
|
(isNaN((buffer = parseInt(node.element.style.left))) ? 0 : buffer) +
|
||||||
|
node.element.offsetWidth / 2
|
||||||
|
);
|
||||||
|
|
||||||
|
// Запись отступа (координаты по вертикали)
|
||||||
|
this.element.children[0].setAttribute(
|
||||||
|
y,
|
||||||
|
(isNaN((buffer = parseInt(node.element.style.top))) ? 0 : buffer) +
|
||||||
|
node.element.offsetHeight / 2
|
||||||
|
);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
// Класс соединения
|
||||||
|
get connection() {
|
||||||
|
return this.#connection;
|
||||||
|
}
|
||||||
|
|
||||||
#move = true;
|
#move = true;
|
||||||
#camera = true;
|
#camera = true;
|
||||||
|
|
||||||
|
@ -362,7 +480,7 @@ class graph {
|
||||||
// Получен обязательный входной параметр в правильном типе
|
// Получен обязательный входной параметр в правильном типе
|
||||||
|
|
||||||
// Инициализация узла
|
// Инициализация узла
|
||||||
const node = new this.node(data, this);
|
const node = new this.node(this, data);
|
||||||
|
|
||||||
// Инициализация ссылки на обрабатываемый объект
|
// Инициализация ссылки на обрабатываемый объект
|
||||||
const _this = this;
|
const _this = this;
|
||||||
|
@ -434,52 +552,20 @@ class graph {
|
||||||
if (from instanceof this.node && to instanceof this.node) {
|
if (from instanceof this.node && to instanceof this.node) {
|
||||||
// Получены обязательные входные параметры в правильном типе
|
// Получены обязательные входные параметры в правильном типе
|
||||||
|
|
||||||
// Инициализация оболочки
|
// Инициализация соединения
|
||||||
const svg = document.createElementNS("http://www.w3.org/2000/svg", "svg");
|
const connection = new this.connection(this, from, to);
|
||||||
svg.id = this.connections.size;
|
|
||||||
svg.classList.add("connection");
|
|
||||||
svg.setAttribute("data-from", from.element.id);
|
|
||||||
svg.setAttribute("data-to", to.element.id);
|
|
||||||
|
|
||||||
// Инициализация координат для линии
|
|
||||||
let x1 = parseInt(from.element.style.left);
|
|
||||||
x1 = isNaN(x1) ? 0 : x1;
|
|
||||||
let y1 = parseInt(from.element.style.top);
|
|
||||||
y1 = isNaN(y1) ? 0 : y1;
|
|
||||||
let x2 = parseInt(to.element.style.left);
|
|
||||||
x2 = isNaN(x2) ? 0 : x2;
|
|
||||||
let y2 = parseInt(to.element.style.top);
|
|
||||||
y2 = isNaN(y2) ? 0 : y2;
|
|
||||||
|
|
||||||
// Инициализация оболочки
|
|
||||||
const line = document.createElementNS(
|
|
||||||
"http://www.w3.org/2000/svg",
|
|
||||||
"line"
|
|
||||||
);
|
|
||||||
line.setAttribute("x1", x1 + from.element.offsetWidth / 2);
|
|
||||||
line.setAttribute("y1", y1 + from.element.offsetHeight / 2);
|
|
||||||
line.setAttribute("x2", x2 + to.element.offsetWidth / 2);
|
|
||||||
line.setAttribute("y2", y2 + to.element.offsetHeight / 2);
|
|
||||||
line.setAttribute("stroke", "grey");
|
|
||||||
line.setAttribute("stroke-width", "8px");
|
|
||||||
|
|
||||||
// Запись в оболочку
|
|
||||||
svg.append(line);
|
|
||||||
|
|
||||||
// Запись в документ
|
|
||||||
this.shell.appendChild(svg);
|
|
||||||
|
|
||||||
// Запись соединений в реестры узлов
|
// Запись соединений в реестры узлов
|
||||||
from.outputs.set(svg, to);
|
from.outputs.add(connection);
|
||||||
to.inputs.set(svg, from);
|
to.inputs.add(connection);
|
||||||
|
|
||||||
// Запись в реестр ядра
|
// Запись в реестр ядра
|
||||||
this.connections.add([from, to]);
|
this.connections.add(connection);
|
||||||
|
|
||||||
// Реинициализация узла-получателя
|
// Реинициализация узла-получателя
|
||||||
to.init(1);
|
to.init(1);
|
||||||
|
|
||||||
return svg;
|
return connection;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue