@yuneta/gobj-ui 7.23.80 → 7.23.82
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +62 -27
- package/dist/gobj-ui.cjs.js +590 -110
- package/dist/gobj-ui.es.js +591 -111
- package/package.json +1 -1
- package/src/c_g6_nodes_tree.js +632 -74
- package/src/c_yui_treedb_graph.js +58 -30
- package/src/lib_graph.css +2 -0
package/dist/gobj-ui.es.js
CHANGED
|
@@ -6,7 +6,7 @@ import { createJSONEditor } from "vanilla-jsoneditor";
|
|
|
6
6
|
import { TabulatorFull } from "tabulator-tables";
|
|
7
7
|
import * as maplibregl from "maplibre-gl";
|
|
8
8
|
import uPlot from "uplot";
|
|
9
|
-
import { BaseLayout, BrushSelect, CanvasEvent, Circle, CommonEvent, DragCanvas, EdgeEvent, ExtensionCategory, Graph, HistoryEvent, NodeEvent, Toolbar, ZoomCanvas, register } from "@antv/g6";
|
|
9
|
+
import { BaseLayout, BrushSelect, CanvasEvent, Circle, CommonEvent, DragCanvas, EdgeEvent, ExtensionCategory, Graph, HTML, HistoryEvent, NodeEvent, Toolbar, ZoomCanvas, register } from "@antv/g6";
|
|
10
10
|
//#region \0rolldown/runtime.js
|
|
11
11
|
var __create = Object.create;
|
|
12
12
|
var __defProp = Object.defineProperty;
|
|
@@ -43154,7 +43154,7 @@ var _excluded$5 = ["style"];
|
|
|
43154
43154
|
* HTML container
|
|
43155
43155
|
* @see https://github.com/pmndrs/drei#html
|
|
43156
43156
|
*/
|
|
43157
|
-
var HTML = /*#__PURE__*/ function(_DisplayObject) {
|
|
43157
|
+
var HTML$1 = /*#__PURE__*/ function(_DisplayObject) {
|
|
43158
43158
|
function HTML() {
|
|
43159
43159
|
var _this;
|
|
43160
43160
|
var _ref = arguments.length > 0 && arguments[0] !== void 0 ? arguments[0] : {}, style = _ref.style, rest = _objectWithoutProperties(_ref, _excluded$5);
|
|
@@ -43202,7 +43202,7 @@ var HTML = /*#__PURE__*/ function(_DisplayObject) {
|
|
|
43202
43202
|
}
|
|
43203
43203
|
]);
|
|
43204
43204
|
}(DisplayObject);
|
|
43205
|
-
HTML.PARSED_STYLE_LIST = new Set([].concat(_toConsumableArray(DisplayObject.PARSED_STYLE_LIST), [
|
|
43205
|
+
HTML$1.PARSED_STYLE_LIST = new Set([].concat(_toConsumableArray(DisplayObject.PARSED_STYLE_LIST), [
|
|
43206
43206
|
"x",
|
|
43207
43207
|
"y",
|
|
43208
43208
|
"$el",
|
|
@@ -54525,11 +54525,31 @@ var SELECT_RING = "rgba(59,130,246,0.95)";
|
|
|
54525
54525
|
var PORT_R_ENTITY = 14;
|
|
54526
54526
|
var PORT_R_CHILD = 8;
|
|
54527
54527
|
var PORT_LINE_WIDTH = 2;
|
|
54528
|
-
var
|
|
54528
|
+
var NODE_MODES$1 = [
|
|
54529
|
+
"expanded",
|
|
54530
|
+
"compact",
|
|
54531
|
+
"shape"
|
|
54532
|
+
];
|
|
54533
|
+
var PILL_SIZE = {
|
|
54534
|
+
hierarchical: [200, 30],
|
|
54535
|
+
extended: [180, 28],
|
|
54536
|
+
child: [160, 26]
|
|
54537
|
+
};
|
|
54538
|
+
var PORT_R_PILL = 6;
|
|
54539
|
+
var SHAPE_SIZE = {
|
|
54529
54540
|
hierarchical: 32,
|
|
54530
54541
|
extended: 28,
|
|
54531
54542
|
child: 22
|
|
54532
54543
|
};
|
|
54544
|
+
var NODE_SHAPES = [
|
|
54545
|
+
"square",
|
|
54546
|
+
"circle",
|
|
54547
|
+
"diamond",
|
|
54548
|
+
"triangle",
|
|
54549
|
+
"hexagon",
|
|
54550
|
+
"star"
|
|
54551
|
+
];
|
|
54552
|
+
var DEFAULT_NODE_SHAPE = "square";
|
|
54533
54553
|
/***************************************************************
|
|
54534
54554
|
* Internal layout and operation mode definitions
|
|
54535
54555
|
***************************************************************/
|
|
@@ -54610,8 +54630,8 @@ var attrs_table$4 = [
|
|
|
54610
54630
|
SDATA(data_type_t.DTP_LIST, "hidden_topics", 0, "[]", "Topics left out of the tree: no card, no pill counts them, no edge reaches them"),
|
|
54611
54631
|
SDATA(data_type_t.DTP_STRING, "main_topic", 0, "", "The topic the tree hangs from; empty = deduced (the one whose hooks reach the most others). Its parentless records are the roots; a parentless record of a topic linked to it is LOOSE and shown only on request"),
|
|
54612
54632
|
SDATA(data_type_t.DTP_LIST, "loose_topics", 0, "[]", "Topics whose loose records (no parent, in a topic the schema hangs from the main one) are shown as roots"),
|
|
54613
|
-
SDATA(data_type_t.DTP_STRING, "node_mode", 0, "expanded", "How a record is drawn: `expanded` = the card with its ports
|
|
54614
|
-
SDATA(data_type_t.DTP_BOOLEAN, "node_labels", 0, true, "A
|
|
54633
|
+
SDATA(data_type_t.DTP_STRING, "node_mode", 0, "expanded", "How a record is drawn: `expanded` = the card with its pills and ports; `compact` = a one-line pill with the name and small ports; `shape` = a figure of the topic's colour (square, circle, diamond... per node or topic, from the node properties), no ports, no text -- the topology alone. One node can be toggled against it (EV_TOGGLE_NODE_MODE)"),
|
|
54634
|
+
SDATA(data_type_t.DTP_BOOLEAN, "node_labels", 0, true, "A `shape` node says its name under the figure. Off, it is a coloured figure and nothing else"),
|
|
54615
54635
|
SDATA(data_type_t.DTP_BOOLEAN, "confirm_delete_node", 0, true, "Ask confirmation before deleting a node"),
|
|
54616
54636
|
SDATA(data_type_t.DTP_BOOLEAN, "confirm_unlink_edge", 0, true, "Ask confirmation before unlinking an edge"),
|
|
54617
54637
|
SDATA(data_type_t.DTP_STRING, "wide", 0, "40px", "Height of header"),
|
|
@@ -54653,6 +54673,8 @@ var PRIVATE_DATA$4 = {
|
|
|
54653
54673
|
_edge_icon_el: null,
|
|
54654
54674
|
_edge_delete_el: null,
|
|
54655
54675
|
_edge_popover_el: null,
|
|
54676
|
+
_port_icon_el: null,
|
|
54677
|
+
_port_popover_el: null,
|
|
54656
54678
|
_node_icon_el: null,
|
|
54657
54679
|
_node_delete_el: null,
|
|
54658
54680
|
_node_popover_el: null,
|
|
@@ -54843,6 +54865,7 @@ function register_layouts(gobj) {
|
|
|
54843
54865
|
register(ExtensionCategory.LAYOUT, "treedb-tree", TreedbTreeLayout);
|
|
54844
54866
|
register(ExtensionCategory.LAYOUT, "treedb-radial", TreedbRadialLayout);
|
|
54845
54867
|
register(ExtensionCategory.NODE, "light", LightNode);
|
|
54868
|
+
register(ExtensionCategory.NODE, "treedb-card", TreedbCard);
|
|
54846
54869
|
}
|
|
54847
54870
|
}
|
|
54848
54871
|
/************************************************************
|
|
@@ -54912,6 +54935,7 @@ function configure_events(gobj) {
|
|
|
54912
54935
|
update_edge_icon_position(gobj);
|
|
54913
54936
|
update_node_icon_position(gobj);
|
|
54914
54937
|
update_link_icon_position(gobj);
|
|
54938
|
+
update_port_icon_position(gobj);
|
|
54915
54939
|
});
|
|
54916
54940
|
graph.on(NodeEvent.DRAG_END, (evt) => {
|
|
54917
54941
|
gobj_send_event(gobj, "EV_NODE_DRAG_END", { evt }, gobj);
|
|
@@ -54936,6 +54960,7 @@ function configure_events(gobj) {
|
|
|
54936
54960
|
update_edge_icon_position(gobj);
|
|
54937
54961
|
update_node_icon_position(gobj);
|
|
54938
54962
|
update_link_icon_position(gobj);
|
|
54963
|
+
update_port_icon_position(gobj);
|
|
54939
54964
|
update_zoom_readout(gobj);
|
|
54940
54965
|
let z = priv.last_zoom;
|
|
54941
54966
|
try {
|
|
@@ -55584,14 +55609,26 @@ function create_topic_node(gobj, desc, record) {
|
|
|
55584
55609
|
* the other one would leave behind (`labelText`, `ports`).
|
|
55585
55610
|
************************************************************/
|
|
55586
55611
|
function node_shape_of(gobj, node_id, desc, record, geometry, pills_html) {
|
|
55587
|
-
|
|
55588
|
-
|
|
55612
|
+
switch (node_mode_of(gobj, node_id)) {
|
|
55613
|
+
case "shape": return figure_shape_of(gobj, desc, record, geometry, {});
|
|
55614
|
+
case "compact": return pill_shape_of(gobj, desc, record, geometry);
|
|
55615
|
+
default: return card_shape_of(gobj, desc, record, geometry, pills_html);
|
|
55616
|
+
}
|
|
55589
55617
|
}
|
|
55590
|
-
function
|
|
55618
|
+
function node_mode_of(gobj, node_id) {
|
|
55591
55619
|
let priv = gobj.priv;
|
|
55592
55620
|
if (!priv._open_nodes) priv._open_nodes = /* @__PURE__ */ new Set();
|
|
55593
|
-
let
|
|
55594
|
-
|
|
55621
|
+
let mode = gobj_read_str_attr(gobj, "node_mode");
|
|
55622
|
+
if (!mode || !str_in_list(NODE_MODES$1, mode)) mode = "expanded";
|
|
55623
|
+
if (priv._open_nodes.has(node_id)) return mode === "expanded" ? "compact" : "expanded";
|
|
55624
|
+
return mode;
|
|
55625
|
+
}
|
|
55626
|
+
function node_is_compact(gobj, node_id) {
|
|
55627
|
+
return node_mode_of(gobj, node_id) !== "expanded";
|
|
55628
|
+
}
|
|
55629
|
+
function topic_defaults_of(gobj, topic_name) {
|
|
55630
|
+
let topic_props = gobj.priv._graph_properties[topic_name];
|
|
55631
|
+
return is_object(topic_props) && is_object(topic_props.defaults) ? topic_props.defaults : null;
|
|
55595
55632
|
}
|
|
55596
55633
|
/************************************************************
|
|
55597
55634
|
* The CARD: an html node, the tier's size, the ports, the
|
|
@@ -55637,45 +55674,107 @@ function card_shape_of(gobj, desc, record, geometry, pills_html) {
|
|
|
55637
55674
|
style.dy = -(saved_size.length > 1 ? saved_size[1] : saved_size[0]) / 2;
|
|
55638
55675
|
}
|
|
55639
55676
|
if (geometry.portR > 0) style.portR = geometry.portR;
|
|
55640
|
-
|
|
55641
|
-
|
|
55642
|
-
|
|
55643
|
-
|
|
55644
|
-
|
|
55645
|
-
|
|
55646
|
-
|
|
55647
|
-
|
|
55648
|
-
|
|
55649
|
-
|
|
55650
|
-
|
|
55651
|
-
|
|
55652
|
-
|
|
55653
|
-
|
|
55654
|
-
|
|
55655
|
-
} else {
|
|
55677
|
+
dress_ports(gobj, style, ports, geometry, topic_defaults, node_treedb_type === "child" ? PORT_R_CHILD : PORT_R_ENTITY, false);
|
|
55678
|
+
return {
|
|
55679
|
+
type: "treedb-card",
|
|
55680
|
+
style
|
|
55681
|
+
};
|
|
55682
|
+
}
|
|
55683
|
+
/************************************************************
|
|
55684
|
+
* The ports of a card or a pill, dressed: the node-level radius
|
|
55685
|
+
* (saved, topic default, or the tier's), each port's own radius
|
|
55686
|
+
* and shape (saved first, then the topic's per-port defaults, then
|
|
55687
|
+
* the topic's one shape for every port). `fixed_r` -- the pill --
|
|
55688
|
+
* ignores every saved radius: a pill has one size of port.
|
|
55689
|
+
************************************************************/
|
|
55690
|
+
function dress_ports(gobj, style, ports, geometry, topic_defaults, r_default, fixed_r) {
|
|
55691
|
+
if (!json_size(ports)) {
|
|
55656
55692
|
style.port = false;
|
|
55657
55693
|
style.ports = [];
|
|
55694
|
+
return;
|
|
55658
55695
|
}
|
|
55696
|
+
json_object_update_missing(style, {
|
|
55697
|
+
port: true,
|
|
55698
|
+
ports,
|
|
55699
|
+
portR: r_default,
|
|
55700
|
+
portLineWidth: PORT_LINE_WIDTH
|
|
55701
|
+
});
|
|
55702
|
+
if (fixed_r) style.portR = r_default;
|
|
55703
|
+
let port_sizes = fixed_r ? null : geometry.port_sizes;
|
|
55704
|
+
let default_port_sizes = !fixed_r && topic_defaults ? topic_defaults.port_sizes : null;
|
|
55705
|
+
let port_shapes = geometry.port_shapes;
|
|
55706
|
+
let default_port_shapes = topic_defaults ? topic_defaults.port_shapes : null;
|
|
55707
|
+
let default_shape = topic_defaults ? topic_defaults.port_shape : null;
|
|
55708
|
+
for (let i = 0; i < style.ports.length; i++) {
|
|
55709
|
+
let key = style.ports[i].key;
|
|
55710
|
+
let r = is_object(port_sizes) ? port_sizes[key] : null;
|
|
55711
|
+
if (r == null && is_object(default_port_sizes)) r = default_port_sizes[key];
|
|
55712
|
+
if (r != null) style.ports[i].r = r;
|
|
55713
|
+
let shape = is_object(port_shapes) ? port_shapes[key] : null;
|
|
55714
|
+
if (!shape && is_object(default_port_shapes)) shape = default_port_shapes[key];
|
|
55715
|
+
if (!shape) shape = default_shape;
|
|
55716
|
+
if (shape && str_in_list(PORT_SHAPES, shape)) style.ports[i].shape = shape;
|
|
55717
|
+
}
|
|
55718
|
+
}
|
|
55719
|
+
/************************************************************
|
|
55720
|
+
* The PILL: one line with the name inside, the tint and the
|
|
55721
|
+
* border of the topic, small ports on its edges -- the half-way
|
|
55722
|
+
* house between the card and the figure, and the same one-line
|
|
55723
|
+
* chip a leaf record already is, at the tier's width. No pills:
|
|
55724
|
+
* a hook is opened from the card (expand the node).
|
|
55725
|
+
************************************************************/
|
|
55726
|
+
function pill_shape_of(gobj, desc, record, geometry) {
|
|
55727
|
+
let priv = gobj.priv;
|
|
55728
|
+
let size = PILL_SIZE[desc.node_treedb_type] || PILL_SIZE.hierarchical;
|
|
55729
|
+
let ports = build_ports(gobj, desc);
|
|
55730
|
+
let style = {
|
|
55731
|
+
fill: desc.color,
|
|
55732
|
+
stroke: getStrokeColor(desc.color),
|
|
55733
|
+
lineWidth: 1,
|
|
55734
|
+
lineDash: [],
|
|
55735
|
+
halo: false,
|
|
55736
|
+
labelText: "",
|
|
55737
|
+
size: [...size],
|
|
55738
|
+
dx: -size[0] / 2,
|
|
55739
|
+
dy: -size[1] / 2,
|
|
55740
|
+
innerHTML: build_chip_innerHTML(desc.color, priv.theme, record.icon, node_label(desc, record), record.id)
|
|
55741
|
+
};
|
|
55742
|
+
dress_ports(gobj, style, ports, geometry, topic_defaults_of(gobj, desc.topic_name), PORT_R_PILL, true);
|
|
55659
55743
|
return {
|
|
55660
|
-
type: "
|
|
55744
|
+
type: "treedb-card",
|
|
55661
55745
|
style
|
|
55662
55746
|
};
|
|
55663
55747
|
}
|
|
55748
|
+
function pill_innerHTML_of(gobj, nd, theme, highlight, selected, anchored) {
|
|
55749
|
+
let desc = nd.data.desc;
|
|
55750
|
+
let record = nd.data.record || {};
|
|
55751
|
+
return build_chip_innerHTML(desc.color, theme, record.icon, node_label(desc, record), record.id, highlight, selected, anchored);
|
|
55752
|
+
}
|
|
55753
|
+
function node_figure_of(gobj, desc, geometry) {
|
|
55754
|
+
let shape = geometry ? geometry.node_shape : null;
|
|
55755
|
+
if (!shape) {
|
|
55756
|
+
let defaults = topic_defaults_of(gobj, desc.topic_name);
|
|
55757
|
+
shape = defaults ? defaults.node_shape : null;
|
|
55758
|
+
}
|
|
55759
|
+
return shape && str_in_list(NODE_SHAPES, shape) ? shape : DEFAULT_NODE_SHAPE;
|
|
55760
|
+
}
|
|
55664
55761
|
/************************************************************
|
|
55665
|
-
* The
|
|
55666
|
-
*
|
|
55667
|
-
*
|
|
55668
|
-
*
|
|
55669
|
-
*
|
|
55762
|
+
* The FIGURE: a native G6 node of the topic's colour -- a square,
|
|
55763
|
+
* a circle, a diamond, a triangle, a hexagon, a star -- no ports,
|
|
55764
|
+
* the name as a label under it when `node_labels` says so. Native
|
|
55765
|
+
* and not html on purpose: G6's own stroke and halo paint on it,
|
|
55766
|
+
* so the focus, the selection and the anchor are three keys of
|
|
55767
|
+
* the style instead of a rebuilt innerHTML.
|
|
55670
55768
|
*
|
|
55671
55769
|
* flags {highlight, selected, anchored}
|
|
55672
55770
|
************************************************************/
|
|
55673
|
-
function
|
|
55771
|
+
function figure_shape_of(gobj, desc, record, geometry, flags) {
|
|
55674
55772
|
let dark = gobj.priv.theme === "dark";
|
|
55675
55773
|
let f = flags || {};
|
|
55676
55774
|
let tier = desc.node_treedb_type;
|
|
55677
|
-
let side =
|
|
55775
|
+
let side = SHAPE_SIZE[tier] || SHAPE_SIZE.hierarchical;
|
|
55678
55776
|
let labels = gobj_read_bool_attr(gobj, "node_labels");
|
|
55777
|
+
let figure = node_figure_of(gobj, desc, geometry || {});
|
|
55679
55778
|
let stroke = getStrokeColor(desc.color);
|
|
55680
55779
|
let line_width = 1.5;
|
|
55681
55780
|
if (f.selected) {
|
|
@@ -55692,34 +55791,35 @@ function compact_shape_of(gobj, desc, record, flags) {
|
|
|
55692
55791
|
dash = [2, 2];
|
|
55693
55792
|
line_width = Math.max(line_width, 2.5);
|
|
55694
55793
|
}
|
|
55794
|
+
let style = {
|
|
55795
|
+
size: [side, side],
|
|
55796
|
+
radius: figure === "square" ? Math.round(side / 5) : 0,
|
|
55797
|
+
fill: desc.color,
|
|
55798
|
+
stroke,
|
|
55799
|
+
lineWidth: line_width,
|
|
55800
|
+
lineDash: dash,
|
|
55801
|
+
halo: !!f.highlight,
|
|
55802
|
+
haloStroke: HIGHLIGHT_HALO,
|
|
55803
|
+
haloLineWidth: 8,
|
|
55804
|
+
port: false,
|
|
55805
|
+
ports: [],
|
|
55806
|
+
labelText: labels ? node_label(desc, record) : "",
|
|
55807
|
+
labelPlacement: "bottom",
|
|
55808
|
+
labelFontSize: 11,
|
|
55809
|
+
labelFill: dark ? "#e6e9ef" : "#2e333d",
|
|
55810
|
+
labelMaxWidth: 150,
|
|
55811
|
+
labelWordWrap: true,
|
|
55812
|
+
labelMaxLines: 1,
|
|
55813
|
+
labelTextOverflow: "ellipsis",
|
|
55814
|
+
labelBackground: true,
|
|
55815
|
+
labelBackgroundFill: dark ? "#1b2230" : "#ffffff",
|
|
55816
|
+
labelBackgroundOpacity: .85,
|
|
55817
|
+
labelBackgroundRadius: 3,
|
|
55818
|
+
labelPadding: [1, 3]
|
|
55819
|
+
};
|
|
55695
55820
|
return {
|
|
55696
|
-
type: "rect",
|
|
55697
|
-
style
|
|
55698
|
-
size: [side, side],
|
|
55699
|
-
radius: Math.round(side / 5),
|
|
55700
|
-
fill: desc.color,
|
|
55701
|
-
stroke,
|
|
55702
|
-
lineWidth: line_width,
|
|
55703
|
-
lineDash: dash,
|
|
55704
|
-
halo: !!f.highlight,
|
|
55705
|
-
haloStroke: HIGHLIGHT_HALO,
|
|
55706
|
-
haloLineWidth: 8,
|
|
55707
|
-
port: false,
|
|
55708
|
-
ports: [],
|
|
55709
|
-
labelText: labels ? node_label(desc, record) : "",
|
|
55710
|
-
labelPlacement: "bottom",
|
|
55711
|
-
labelFontSize: 11,
|
|
55712
|
-
labelFill: dark ? "#e6e9ef" : "#2e333d",
|
|
55713
|
-
labelMaxWidth: 150,
|
|
55714
|
-
labelWordWrap: true,
|
|
55715
|
-
labelMaxLines: 1,
|
|
55716
|
-
labelTextOverflow: "ellipsis",
|
|
55717
|
-
labelBackground: true,
|
|
55718
|
-
labelBackgroundFill: dark ? "#1b2230" : "#ffffff",
|
|
55719
|
-
labelBackgroundOpacity: .85,
|
|
55720
|
-
labelBackgroundRadius: 3,
|
|
55721
|
-
labelPadding: [1, 3]
|
|
55722
|
-
}
|
|
55821
|
+
type: figure === "square" ? "rect" : figure,
|
|
55822
|
+
style
|
|
55723
55823
|
};
|
|
55724
55824
|
}
|
|
55725
55825
|
/************************************************************
|
|
@@ -56081,6 +56181,10 @@ function update_geometry(gobj, node_id) {
|
|
|
56081
56181
|
for (let i = 0; i < ports.length; i++) if (ports[i].r != null) port_sizes[ports[i].key] = ports[i].r;
|
|
56082
56182
|
if (Object.keys(port_sizes).length > 0) node_props.port_sizes = port_sizes;
|
|
56083
56183
|
else delete node_props.port_sizes;
|
|
56184
|
+
let port_shapes = {};
|
|
56185
|
+
for (let i = 0; i < ports.length; i++) if (ports[i].shape && ports[i].shape !== "circle") port_shapes[ports[i].key] = ports[i].shape;
|
|
56186
|
+
if (Object.keys(port_shapes).length > 0) node_props.port_shapes = port_shapes;
|
|
56187
|
+
else delete node_props.port_shapes;
|
|
56084
56188
|
}
|
|
56085
56189
|
topic_props.nodes[record.id] = node_props;
|
|
56086
56190
|
nodedata.data.graph_props = node_props;
|
|
@@ -56563,11 +56667,74 @@ function graph_resize(gobj, width, height) {
|
|
|
56563
56667
|
update_port_resize_handles_position(gobj);
|
|
56564
56668
|
update_node_icon_position(gobj);
|
|
56565
56669
|
update_link_icon_position(gobj);
|
|
56670
|
+
update_port_icon_position(gobj);
|
|
56566
56671
|
}
|
|
56567
56672
|
function graph_write_behaviors(gobj, behaviors) {
|
|
56568
56673
|
gobj.priv.graph.setOptions({ behaviors });
|
|
56569
56674
|
}
|
|
56570
56675
|
/************************************************************
|
|
56676
|
+
* Custom G6 node: TreedbCard -- G6's html node with ports that
|
|
56677
|
+
* have a SHAPE.
|
|
56678
|
+
*
|
|
56679
|
+
* G6 draws every port as a circle (`drawPortShapes` upserts a
|
|
56680
|
+
* `Circle`, nothing in the port style says otherwise). A port's
|
|
56681
|
+
* `shape` -- `circle`, `square`, `diamond`, `triangle` -- picks
|
|
56682
|
+
* the G shape here, by the names G6 registers itself, and `r`
|
|
56683
|
+
* stays the one size: the half-side of the square, the half-
|
|
56684
|
+
* diagonal of the diamond, the half-height of the triangle. The
|
|
56685
|
+
* hit test, the resize handles and the edge's landing point all
|
|
56686
|
+
* read `r` and none of them care about the outline.
|
|
56687
|
+
************************************************************/
|
|
56688
|
+
var PORT_SHAPES = [
|
|
56689
|
+
"circle",
|
|
56690
|
+
"square",
|
|
56691
|
+
"diamond",
|
|
56692
|
+
"triangle"
|
|
56693
|
+
];
|
|
56694
|
+
var TreedbCard = class extends HTML {
|
|
56695
|
+
drawPortShapes(attributes, container) {
|
|
56696
|
+
const portsStyle = this.getPortsStyle(attributes);
|
|
56697
|
+
Object.keys(portsStyle).forEach((key) => {
|
|
56698
|
+
const style = portsStyle[key];
|
|
56699
|
+
const shapeKey = `port-${key}`;
|
|
56700
|
+
if (style === false) {
|
|
56701
|
+
this.upsert(shapeKey, "circle", false, container);
|
|
56702
|
+
return;
|
|
56703
|
+
}
|
|
56704
|
+
let r = Number(style.r) || 0;
|
|
56705
|
+
switch (style.shape) {
|
|
56706
|
+
case "square":
|
|
56707
|
+
this.upsert(shapeKey, "rect", Object.assign({}, style, {
|
|
56708
|
+
x: -r,
|
|
56709
|
+
y: -r,
|
|
56710
|
+
width: 2 * r,
|
|
56711
|
+
height: 2 * r
|
|
56712
|
+
}), container);
|
|
56713
|
+
break;
|
|
56714
|
+
case "diamond":
|
|
56715
|
+
this.upsert(shapeKey, "polygon", Object.assign({}, style, { points: [
|
|
56716
|
+
[0, -r],
|
|
56717
|
+
[r, 0],
|
|
56718
|
+
[0, r],
|
|
56719
|
+
[-r, 0]
|
|
56720
|
+
] }), container);
|
|
56721
|
+
break;
|
|
56722
|
+
case "triangle":
|
|
56723
|
+
this.upsert(shapeKey, "polygon", Object.assign({}, style, { points: [
|
|
56724
|
+
[0, -r],
|
|
56725
|
+
[r, r],
|
|
56726
|
+
[-r, r]
|
|
56727
|
+
] }), container);
|
|
56728
|
+
break;
|
|
56729
|
+
default: this.upsert(shapeKey, "circle", style, container);
|
|
56730
|
+
}
|
|
56731
|
+
});
|
|
56732
|
+
}
|
|
56733
|
+
};
|
|
56734
|
+
function is_card_type(type) {
|
|
56735
|
+
return type === "treedb-card" || type === "html";
|
|
56736
|
+
}
|
|
56737
|
+
/************************************************************
|
|
56571
56738
|
* Custom G6 node: LightNode (circle with status indicator)
|
|
56572
56739
|
************************************************************/
|
|
56573
56740
|
var LightNode = class extends Circle {
|
|
@@ -57313,7 +57480,7 @@ function start_node_resize(gobj, e, mx, my) {
|
|
|
57313
57480
|
};
|
|
57314
57481
|
if (nodeType === "circle") updateStyle.size = [Math.max(newW, newH)];
|
|
57315
57482
|
else updateStyle.size = [newW, newH];
|
|
57316
|
-
if (nodeType
|
|
57483
|
+
if (is_card_type(nodeType)) {
|
|
57317
57484
|
updateStyle.dx = -newW / 2;
|
|
57318
57485
|
updateStyle.dy = -newH / 2;
|
|
57319
57486
|
}
|
|
@@ -57438,6 +57605,7 @@ function select_port(gobj, node_id, port_key) {
|
|
|
57438
57605
|
priv._selected_port_key = port_key;
|
|
57439
57606
|
show_port_resize_handles(gobj);
|
|
57440
57607
|
show_link_icon_if_fkey(gobj);
|
|
57608
|
+
show_port_icon(gobj);
|
|
57441
57609
|
}
|
|
57442
57610
|
/************************************************************
|
|
57443
57611
|
* Deselect port: clear port state, return to node selection.
|
|
@@ -57446,6 +57614,8 @@ function deselect_port(gobj) {
|
|
|
57446
57614
|
let priv = gobj.priv;
|
|
57447
57615
|
exit_linking_mode(gobj);
|
|
57448
57616
|
hide_link_icon(gobj);
|
|
57617
|
+
hide_port_icon(gobj);
|
|
57618
|
+
hide_port_popover(gobj);
|
|
57449
57619
|
hide_port_resize_handles(gobj);
|
|
57450
57620
|
priv._selected_port_key = null;
|
|
57451
57621
|
}
|
|
@@ -57498,6 +57668,217 @@ function update_link_icon_position(gobj) {
|
|
|
57498
57668
|
}
|
|
57499
57669
|
}
|
|
57500
57670
|
/************************************************************
|
|
57671
|
+
* Port properties icon and popover: the gear beside a selected
|
|
57672
|
+
* port, as the node has its own. The popover has the two things
|
|
57673
|
+
* a port IS on screen -- its shape and its radius -- and the
|
|
57674
|
+
* scope: this port, the same port of every card of the topic
|
|
57675
|
+
* (the hook or fkey column), or every port there is.
|
|
57676
|
+
************************************************************/
|
|
57677
|
+
function port_icon_xy(gobj) {
|
|
57678
|
+
let priv = gobj.priv;
|
|
57679
|
+
let graph = priv.graph;
|
|
57680
|
+
let canvasPos = get_port_canvas_position(gobj, priv._selected_node_id, priv._selected_port_key);
|
|
57681
|
+
if (!canvasPos) return null;
|
|
57682
|
+
let vp = graph.getViewportByCanvas([canvasPos.x, canvasPos.y]);
|
|
57683
|
+
let below = priv._link_icon_el ? floating_icon_step() : 0;
|
|
57684
|
+
return {
|
|
57685
|
+
x: vp[0] + floating_icon_size() / 2 + 4,
|
|
57686
|
+
y: vp[1] + floating_icon_dy() + below
|
|
57687
|
+
};
|
|
57688
|
+
}
|
|
57689
|
+
function show_port_icon(gobj) {
|
|
57690
|
+
hide_port_icon(gobj);
|
|
57691
|
+
let priv = gobj.priv;
|
|
57692
|
+
if (!priv._selected_node_id || !priv._selected_port_key) return;
|
|
57693
|
+
let xy = port_icon_xy(gobj);
|
|
57694
|
+
if (!xy) return;
|
|
57695
|
+
let icon = create_floating_icon("gear", "#1890ff", xy.x, xy.y, t("port properties"), () => toggle_port_popover(gobj));
|
|
57696
|
+
priv.$container.appendChild(icon);
|
|
57697
|
+
priv._port_icon_el = icon;
|
|
57698
|
+
}
|
|
57699
|
+
function hide_port_icon(gobj) {
|
|
57700
|
+
hide_overlay(gobj, "_port_icon_el");
|
|
57701
|
+
}
|
|
57702
|
+
function update_port_icon_position(gobj) {
|
|
57703
|
+
let priv = gobj.priv;
|
|
57704
|
+
if (!priv._port_icon_el || !priv._selected_node_id || !priv._selected_port_key) return;
|
|
57705
|
+
try {
|
|
57706
|
+
let xy = port_icon_xy(gobj);
|
|
57707
|
+
if (!xy) {
|
|
57708
|
+
hide_port_icon(gobj);
|
|
57709
|
+
hide_port_popover(gobj);
|
|
57710
|
+
return;
|
|
57711
|
+
}
|
|
57712
|
+
priv._port_icon_el.style.left = xy.x + "px";
|
|
57713
|
+
priv._port_icon_el.style.top = xy.y + "px";
|
|
57714
|
+
if (priv._port_popover_el) {
|
|
57715
|
+
priv._port_popover_el.style.left = xy.x + floating_popover_dx() + "px";
|
|
57716
|
+
priv._port_popover_el.style.top = xy.y + "px";
|
|
57717
|
+
clamp_popover_position(gobj, priv._port_popover_el);
|
|
57718
|
+
}
|
|
57719
|
+
} catch (e) {
|
|
57720
|
+
hide_port_icon(gobj);
|
|
57721
|
+
hide_port_popover(gobj);
|
|
57722
|
+
}
|
|
57723
|
+
}
|
|
57724
|
+
function toggle_port_popover(gobj) {
|
|
57725
|
+
if (gobj.priv._port_popover_el) hide_port_popover(gobj);
|
|
57726
|
+
else show_port_popover(gobj);
|
|
57727
|
+
}
|
|
57728
|
+
function hide_port_popover(gobj) {
|
|
57729
|
+
hide_overlay(gobj, "_port_popover_el");
|
|
57730
|
+
}
|
|
57731
|
+
function ports_with(ports, port_key, changes) {
|
|
57732
|
+
return (ports || []).map((p) => p.key === port_key ? Object.assign({}, p, changes) : p);
|
|
57733
|
+
}
|
|
57734
|
+
function show_port_popover(gobj) {
|
|
57735
|
+
hide_port_popover(gobj);
|
|
57736
|
+
let priv = gobj.priv;
|
|
57737
|
+
let graph = priv.graph;
|
|
57738
|
+
let node_id = priv._selected_node_id;
|
|
57739
|
+
let port_key = priv._selected_port_key;
|
|
57740
|
+
if (!node_id || !port_key) return;
|
|
57741
|
+
let nodeData = graph.getNodeData(node_id);
|
|
57742
|
+
if (!nodeData || !nodeData.style) return;
|
|
57743
|
+
let port = (nodeData.style.ports || []).find((p) => p.key === port_key);
|
|
57744
|
+
if (!port) return;
|
|
57745
|
+
let orig_shape = port.shape || "circle";
|
|
57746
|
+
let orig_r = get_port_radius(gobj, node_id, port_key);
|
|
57747
|
+
let xy = port_icon_xy(gobj);
|
|
57748
|
+
if (!xy) return;
|
|
57749
|
+
const popover = create_popover_base(xy.x + floating_popover_dx(), xy.y, "g6-port-popover", "#d9d9d9", 180);
|
|
57750
|
+
function preview_port() {
|
|
57751
|
+
let r = parseInt(rInput.value) || orig_r;
|
|
57752
|
+
graph.updateNodeData([{
|
|
57753
|
+
id: node_id,
|
|
57754
|
+
style: { ports: ports_with(nodeData.style.ports, port_key, {
|
|
57755
|
+
shape: shapeSelect.value,
|
|
57756
|
+
r
|
|
57757
|
+
}) }
|
|
57758
|
+
}]);
|
|
57759
|
+
graph.draw().then(() => {
|
|
57760
|
+
update_port_resize_handles_position(gobj);
|
|
57761
|
+
});
|
|
57762
|
+
}
|
|
57763
|
+
create_form_label(popover, "shape");
|
|
57764
|
+
let shapeSelect = create_form_select(popover, PORT_SHAPES.map((shape) => {
|
|
57765
|
+
return {
|
|
57766
|
+
value: shape,
|
|
57767
|
+
label: t(shape)
|
|
57768
|
+
};
|
|
57769
|
+
}));
|
|
57770
|
+
shapeSelect.value = orig_shape;
|
|
57771
|
+
shapeSelect.addEventListener("change", preview_port);
|
|
57772
|
+
create_form_label(popover, "radius");
|
|
57773
|
+
let rInput = create_form_number_input(popover, orig_r, 2, 40, preview_port);
|
|
57774
|
+
create_form_label(popover, "apply to");
|
|
57775
|
+
let scopeSelect = create_form_select(popover, [
|
|
57776
|
+
{
|
|
57777
|
+
value: "this",
|
|
57778
|
+
label: t("this port")
|
|
57779
|
+
},
|
|
57780
|
+
{
|
|
57781
|
+
value: "same_topic",
|
|
57782
|
+
label: t("same port in topic")
|
|
57783
|
+
},
|
|
57784
|
+
{
|
|
57785
|
+
value: "all",
|
|
57786
|
+
label: t("all ports")
|
|
57787
|
+
}
|
|
57788
|
+
]);
|
|
57789
|
+
create_form_button_row(popover, [{
|
|
57790
|
+
text: "cancel",
|
|
57791
|
+
style: BTN_STYLE_CANCEL,
|
|
57792
|
+
onClick: () => {
|
|
57793
|
+
graph.updateNodeData([{
|
|
57794
|
+
id: node_id,
|
|
57795
|
+
style: { ports: ports_with(nodeData.style.ports, port_key, {
|
|
57796
|
+
shape: orig_shape,
|
|
57797
|
+
r: orig_r
|
|
57798
|
+
}) }
|
|
57799
|
+
}]);
|
|
57800
|
+
graph.draw().then(() => {
|
|
57801
|
+
update_port_resize_handles_position(gobj);
|
|
57802
|
+
});
|
|
57803
|
+
hide_port_popover(gobj);
|
|
57804
|
+
}
|
|
57805
|
+
}, {
|
|
57806
|
+
text: "apply",
|
|
57807
|
+
style: "flex:1;padding:6px;background:#1890ff;color:#fff;border:none;border-radius:4px;cursor:pointer;font-size:13px;font-weight:500;",
|
|
57808
|
+
onClick: () => {
|
|
57809
|
+
apply_port_properties(gobj, node_id, port_key, shapeSelect.value, parseInt(rInput.value) || orig_r, scopeSelect.value);
|
|
57810
|
+
}
|
|
57811
|
+
}]);
|
|
57812
|
+
priv.$container.appendChild(popover);
|
|
57813
|
+
priv._port_popover_el = popover;
|
|
57814
|
+
clamp_popover_position(gobj, popover);
|
|
57815
|
+
}
|
|
57816
|
+
/************************************************************
|
|
57817
|
+
* Apply a port's shape and radius to one port, to the same port
|
|
57818
|
+
* of every card of the topic, or to every port -- and remember
|
|
57819
|
+
* the choice as the topic's default, the way `resize all ports`
|
|
57820
|
+
* does, so a card that arrives later is born with it.
|
|
57821
|
+
* scope: 'this', 'same_topic', 'all'
|
|
57822
|
+
************************************************************/
|
|
57823
|
+
function apply_port_properties(gobj, node_id, port_key, shape, r, scope) {
|
|
57824
|
+
let priv = gobj.priv;
|
|
57825
|
+
let graph = priv.graph;
|
|
57826
|
+
let nodeData = graph.getNodeData(node_id);
|
|
57827
|
+
if (!nodeData || !nodeData.data) return;
|
|
57828
|
+
let source_topic = nodeData.data.topic_name;
|
|
57829
|
+
if (scope === "same_topic") {
|
|
57830
|
+
if (!is_object(priv._graph_properties[source_topic])) priv._graph_properties[source_topic] = {};
|
|
57831
|
+
let defaults = priv._graph_properties[source_topic].defaults || {};
|
|
57832
|
+
defaults.port_sizes = Object.assign({}, defaults.port_sizes, { [port_key]: r });
|
|
57833
|
+
defaults.port_shapes = Object.assign({}, defaults.port_shapes, { [port_key]: shape });
|
|
57834
|
+
priv._graph_properties[source_topic].defaults = defaults;
|
|
57835
|
+
} else if (scope === "all") for (const topic_name of Object.keys(priv.descs || {})) {
|
|
57836
|
+
if (!is_object(priv._graph_properties[topic_name])) priv._graph_properties[topic_name] = {};
|
|
57837
|
+
let defaults = priv._graph_properties[topic_name].defaults || {};
|
|
57838
|
+
defaults.portR = r;
|
|
57839
|
+
defaults.port_shape = shape;
|
|
57840
|
+
delete defaults.port_sizes;
|
|
57841
|
+
delete defaults.port_shapes;
|
|
57842
|
+
priv._graph_properties[topic_name].defaults = defaults;
|
|
57843
|
+
}
|
|
57844
|
+
let updates = [];
|
|
57845
|
+
for (let nd of graph.getNodeData() || []) {
|
|
57846
|
+
if (!nd || !nd.data || !nd.data.desc || !nd.style || !is_array(nd.style.ports)) continue;
|
|
57847
|
+
let new_ports;
|
|
57848
|
+
if (scope === "this") {
|
|
57849
|
+
if (nd.id !== node_id) continue;
|
|
57850
|
+
new_ports = ports_with(nd.style.ports, port_key, {
|
|
57851
|
+
shape,
|
|
57852
|
+
r
|
|
57853
|
+
});
|
|
57854
|
+
} else if (scope === "same_topic") {
|
|
57855
|
+
if (nd.data.topic_name !== source_topic) continue;
|
|
57856
|
+
new_ports = ports_with(nd.style.ports, port_key, {
|
|
57857
|
+
shape,
|
|
57858
|
+
r
|
|
57859
|
+
});
|
|
57860
|
+
} else new_ports = nd.style.ports.map((p) => Object.assign({}, p, {
|
|
57861
|
+
shape,
|
|
57862
|
+
r
|
|
57863
|
+
}));
|
|
57864
|
+
let upd = { ports: new_ports };
|
|
57865
|
+
if (scope === "all") upd.portR = r;
|
|
57866
|
+
updates.push({
|
|
57867
|
+
id: nd.id,
|
|
57868
|
+
style: upd
|
|
57869
|
+
});
|
|
57870
|
+
}
|
|
57871
|
+
if (updates.length > 0) {
|
|
57872
|
+
graph.updateNodeData(updates);
|
|
57873
|
+
graph.draw().then(() => {
|
|
57874
|
+
update_port_resize_handles_position(gobj);
|
|
57875
|
+
update_port_icon_position(gobj);
|
|
57876
|
+
mark_graph_dirty(gobj);
|
|
57877
|
+
});
|
|
57878
|
+
}
|
|
57879
|
+
hide_port_popover(gobj);
|
|
57880
|
+
}
|
|
57881
|
+
/************************************************************
|
|
57501
57882
|
* Get a column descriptor by field id from a topic desc.
|
|
57502
57883
|
************************************************************/
|
|
57503
57884
|
function get_col_by_id(desc, col_id) {
|
|
@@ -58204,6 +58585,14 @@ function show_node_popover(gobj) {
|
|
|
58204
58585
|
let strokeInput = create_form_color_input(popover, currentStroke, preview_node);
|
|
58205
58586
|
create_form_label(popover, "line width");
|
|
58206
58587
|
let lwInput = create_form_number_input(popover, currentLW, 1, 20, preview_node);
|
|
58588
|
+
create_form_label(popover, "shape");
|
|
58589
|
+
let shapeSelect = create_form_select(popover, NODE_SHAPES.map((shape) => {
|
|
58590
|
+
return {
|
|
58591
|
+
value: shape,
|
|
58592
|
+
label: t(shape)
|
|
58593
|
+
};
|
|
58594
|
+
}));
|
|
58595
|
+
shapeSelect.value = nodeData.data && nodeData.data.desc ? node_figure_of(gobj, nodeData.data.desc, nodeData.data.graph_props || {}) : DEFAULT_NODE_SHAPE;
|
|
58207
58596
|
create_form_label(popover, "apply to");
|
|
58208
58597
|
let scopeSelect = create_form_select(popover, [
|
|
58209
58598
|
{
|
|
@@ -58243,7 +58632,7 @@ function show_node_popover(gobj) {
|
|
|
58243
58632
|
text: "apply",
|
|
58244
58633
|
style: "flex:1;padding:6px;background:#1890ff;color:#fff;border:none;border-radius:4px;cursor:pointer;font-size:13px;font-weight:500;",
|
|
58245
58634
|
onClick: () => {
|
|
58246
|
-
apply_node_properties(gobj, node_id, fillInput.value, strokeInput.value, parseInt(lwInput.value) || 1, scopeSelect.value);
|
|
58635
|
+
apply_node_properties(gobj, node_id, fillInput.value, strokeInput.value, parseInt(lwInput.value) || 1, scopeSelect.value, shapeSelect.value);
|
|
58247
58636
|
}
|
|
58248
58637
|
}]);
|
|
58249
58638
|
priv.$container.appendChild(popover);
|
|
@@ -58474,10 +58863,11 @@ function repaint_cards(gobj, ids) {
|
|
|
58474
58863
|
continue;
|
|
58475
58864
|
}
|
|
58476
58865
|
let anchored = priv.anchor_state === "on" && id === priv.anchor_id;
|
|
58477
|
-
|
|
58866
|
+
let mode = nd && nd.data && nd.data.desc ? node_mode_of(gobj, id) : "expanded";
|
|
58867
|
+
if (mode === "shape") {
|
|
58478
58868
|
updates.push({
|
|
58479
58869
|
id,
|
|
58480
|
-
style:
|
|
58870
|
+
style: figure_shape_of(gobj, nd.data.desc, nd.data.record || {}, nd.data.graph_props || {}, {
|
|
58481
58871
|
highlight: focus.has(id),
|
|
58482
58872
|
selected: selected.has(id),
|
|
58483
58873
|
anchored
|
|
@@ -58485,7 +58875,7 @@ function repaint_cards(gobj, ids) {
|
|
|
58485
58875
|
});
|
|
58486
58876
|
continue;
|
|
58487
58877
|
}
|
|
58488
|
-
let html = node_innerHTML_of(nd, priv.theme, focus.has(id), selected.has(id), anchored, pills_html_of(gobj, nd));
|
|
58878
|
+
let html = mode === "compact" ? pill_innerHTML_of(gobj, nd, priv.theme, focus.has(id), selected.has(id), anchored) : node_innerHTML_of(nd, priv.theme, focus.has(id), selected.has(id), anchored, pills_html_of(gobj, nd));
|
|
58489
58879
|
if (html !== null) updates.push({
|
|
58490
58880
|
id,
|
|
58491
58881
|
style: { innerHTML: html }
|
|
@@ -58523,10 +58913,11 @@ function refresh_html_nodes_theme(gobj, theme) {
|
|
|
58523
58913
|
let id = nodes[i].id;
|
|
58524
58914
|
let nd = graph.getNodeData(id);
|
|
58525
58915
|
let anchored = priv.anchor_state === "on" && id === priv.anchor_id;
|
|
58526
|
-
|
|
58916
|
+
let mode = nd && nd.data && nd.data.desc ? node_mode_of(gobj, id) : "expanded";
|
|
58917
|
+
if (mode === "shape") {
|
|
58527
58918
|
updates.push({
|
|
58528
58919
|
id,
|
|
58529
|
-
style:
|
|
58920
|
+
style: figure_shape_of(gobj, nd.data.desc, nd.data.record || {}, nd.data.graph_props || {}, {
|
|
58530
58921
|
highlight: highlighted.has(id),
|
|
58531
58922
|
selected: selected.has(id),
|
|
58532
58923
|
anchored
|
|
@@ -58534,7 +58925,7 @@ function refresh_html_nodes_theme(gobj, theme) {
|
|
|
58534
58925
|
});
|
|
58535
58926
|
continue;
|
|
58536
58927
|
}
|
|
58537
|
-
let html = node_innerHTML_of(nd, theme, highlighted.has(id), selected.has(id), anchored, pills_html_of(gobj, nd));
|
|
58928
|
+
let html = mode === "compact" ? pill_innerHTML_of(gobj, nd, theme, highlighted.has(id), selected.has(id), anchored) : node_innerHTML_of(nd, theme, highlighted.has(id), selected.has(id), anchored, pills_html_of(gobj, nd));
|
|
58538
58929
|
if (html === null) html = more_innerHTML_of(gobj, nd, theme);
|
|
58539
58930
|
if (html !== null) updates.push({
|
|
58540
58931
|
id,
|
|
@@ -58992,7 +59383,7 @@ function hide_unlink_confirm(gobj) {
|
|
|
58992
59383
|
* Apply node properties to one or more nodes.
|
|
58993
59384
|
* scope: 'this', 'same_topic', 'all'
|
|
58994
59385
|
************************************************************/
|
|
58995
|
-
function apply_node_properties(gobj, node_id, fill, stroke, lineWidth, scope) {
|
|
59386
|
+
function apply_node_properties(gobj, node_id, fill, stroke, lineWidth, scope, shape) {
|
|
58996
59387
|
let priv = gobj.priv;
|
|
58997
59388
|
let graph = priv.graph;
|
|
58998
59389
|
let nodeData = graph.getNodeData(node_id);
|
|
@@ -59000,11 +59391,26 @@ function apply_node_properties(gobj, node_id, fill, stroke, lineWidth, scope) {
|
|
|
59000
59391
|
let source_topic = nodeData.data.desc ? nodeData.data.desc.topic_name : null;
|
|
59001
59392
|
let updates = [];
|
|
59002
59393
|
const nodes = graph.getData().nodes;
|
|
59394
|
+
let figure = shape && str_in_list(NODE_SHAPES, shape) ? shape : "";
|
|
59395
|
+
let reshaped = [];
|
|
59396
|
+
if (figure && scope !== "this") {
|
|
59397
|
+
let topics = scope === "same_topic" ? [source_topic] : Object.keys(priv.descs || {});
|
|
59398
|
+
for (let topic_name of topics) {
|
|
59399
|
+
if (!is_object(priv._graph_properties[topic_name])) priv._graph_properties[topic_name] = {};
|
|
59400
|
+
let defaults = priv._graph_properties[topic_name].defaults || {};
|
|
59401
|
+
defaults.node_shape = figure;
|
|
59402
|
+
priv._graph_properties[topic_name].defaults = defaults;
|
|
59403
|
+
}
|
|
59404
|
+
}
|
|
59003
59405
|
for (let i = 0; i < nodes.length; i++) {
|
|
59004
59406
|
let nd = graph.getNodeData(nodes[i].id);
|
|
59005
59407
|
if (!nd || !nd.data || !nd.data.desc) continue;
|
|
59006
59408
|
if (scope === "this" && nodes[i].id !== node_id) continue;
|
|
59007
59409
|
if (scope === "same_topic" && nd.data.desc.topic_name !== source_topic) continue;
|
|
59410
|
+
if (figure) {
|
|
59411
|
+
node_props_entry(gobj, nd).node_shape = figure;
|
|
59412
|
+
if (node_mode_of(gobj, nodes[i].id) === "shape") reshaped.push(nodes[i].id);
|
|
59413
|
+
}
|
|
59008
59414
|
let updateStyle = {
|
|
59009
59415
|
fill,
|
|
59010
59416
|
stroke,
|
|
@@ -59021,6 +59427,7 @@ function apply_node_properties(gobj, node_id, fill, stroke, lineWidth, scope) {
|
|
|
59021
59427
|
}
|
|
59022
59428
|
if (updates.length > 0) {
|
|
59023
59429
|
graph.updateNodeData(updates);
|
|
59430
|
+
if (reshaped.length) reshape_nodes(gobj, reshaped);
|
|
59024
59431
|
graph.draw().then(() => {
|
|
59025
59432
|
mark_graph_dirty(gobj);
|
|
59026
59433
|
});
|
|
@@ -59028,6 +59435,23 @@ function apply_node_properties(gobj, node_id, fill, stroke, lineWidth, scope) {
|
|
|
59028
59435
|
hide_node_popover(gobj);
|
|
59029
59436
|
}
|
|
59030
59437
|
/************************************************************
|
|
59438
|
+
* The node's entry in `_graph_properties` -- the object Save
|
|
59439
|
+
* reads and writes -- created if it has none yet, and the node's
|
|
59440
|
+
* `data.graph_props` pointed at it, so a key written here is
|
|
59441
|
+
* read by the next reshape and survives the next Save.
|
|
59442
|
+
************************************************************/
|
|
59443
|
+
function node_props_entry(gobj, nd) {
|
|
59444
|
+
let priv = gobj.priv;
|
|
59445
|
+
let topic_name = nd.data.topic_name;
|
|
59446
|
+
let record = nd.data.record || {};
|
|
59447
|
+
if (!is_object(priv._graph_properties[topic_name])) priv._graph_properties[topic_name] = {};
|
|
59448
|
+
let topic_props = priv._graph_properties[topic_name];
|
|
59449
|
+
if (!is_object(topic_props.nodes)) topic_props.nodes = {};
|
|
59450
|
+
if (!is_object(topic_props.nodes[record.id])) topic_props.nodes[record.id] = is_object(nd.data.graph_props) ? nd.data.graph_props : {};
|
|
59451
|
+
nd.data.graph_props = topic_props.nodes[record.id];
|
|
59452
|
+
return nd.data.graph_props;
|
|
59453
|
+
}
|
|
59454
|
+
/************************************************************
|
|
59031
59455
|
* Apply edge properties to one or more edges.
|
|
59032
59456
|
* scope: 'this', 'same_type', 'all'
|
|
59033
59457
|
************************************************************/
|
|
@@ -59155,8 +59579,8 @@ function ctx_item(icon_id, label, value) {
|
|
|
59155
59579
|
function build_node_context_menu(gobj, node_id) {
|
|
59156
59580
|
let items = [];
|
|
59157
59581
|
inject_svg_icons();
|
|
59158
|
-
if (node_is_compact(gobj, node_id)) items.push(ctx_item("g6-icon-fullscreen", t("
|
|
59159
|
-
else items.push(ctx_item("g6-icon-fullscreen-exit", t("
|
|
59582
|
+
if (node_is_compact(gobj, node_id)) items.push(ctx_item("g6-icon-fullscreen", t("expand node"), "toggle_node_mode"));
|
|
59583
|
+
else items.push(ctx_item("g6-icon-fullscreen-exit", t("collapse node"), "toggle_node_mode"));
|
|
59160
59584
|
if (gobj.priv.edit_mode && !node_is_compact(gobj, node_id)) {
|
|
59161
59585
|
items.push(ctx_item("g6-icon-resize", t("resize all"), "resize_all_nodes"));
|
|
59162
59586
|
items.push(ctx_item("g6-icon-resize", t("resize topic nodes"), "resize_topic_nodes"));
|
|
@@ -59172,6 +59596,7 @@ function build_port_context_menu(gobj, node_id, port_key) {
|
|
|
59172
59596
|
let items = [];
|
|
59173
59597
|
if (gobj.priv.edit_mode) {
|
|
59174
59598
|
inject_svg_icons();
|
|
59599
|
+
items.push(ctx_item("g6-icon-edit", t("port properties"), "port_properties"));
|
|
59175
59600
|
items.push(ctx_item("g6-icon-resize", t("resize all ports"), "resize_all_ports"));
|
|
59176
59601
|
items.push(ctx_item("g6-icon-resize", t("resize topic ports"), "resize_topic_ports"));
|
|
59177
59602
|
}
|
|
@@ -59204,6 +59629,12 @@ function handle_context_menu_click(gobj, value) {
|
|
|
59204
59629
|
case "reset_topic_sizes":
|
|
59205
59630
|
reset_sizes(gobj, true);
|
|
59206
59631
|
break;
|
|
59632
|
+
case "port_properties":
|
|
59633
|
+
if (priv._context_node_id && priv._context_port_key) {
|
|
59634
|
+
select_port(gobj, priv._context_node_id, priv._context_port_key);
|
|
59635
|
+
show_port_popover(gobj);
|
|
59636
|
+
}
|
|
59637
|
+
break;
|
|
59207
59638
|
case "resize_all_ports":
|
|
59208
59639
|
copy_size_to_ports(gobj, false);
|
|
59209
59640
|
break;
|
|
@@ -59247,7 +59678,7 @@ function copy_size_to_nodes(gobj, same_topic_only) {
|
|
|
59247
59678
|
if (nodes[i].id === node_id) continue;
|
|
59248
59679
|
let updateStyle = { size: [...source_size] };
|
|
59249
59680
|
if (source_portR != null) updateStyle.portR = source_portR;
|
|
59250
|
-
if (nd.type
|
|
59681
|
+
if (is_card_type(nd.type)) {
|
|
59251
59682
|
updateStyle.dx = -source_size[0] / 2;
|
|
59252
59683
|
updateStyle.dy = -(source_size.length > 1 ? source_size[1] : source_size[0]) / 2;
|
|
59253
59684
|
}
|
|
@@ -59388,7 +59819,7 @@ var MORE_CHIP_SIZE_COMPACT = [40, 22];
|
|
|
59388
59819
|
function more_chip_is_compact(gobj, nd) {
|
|
59389
59820
|
let parent_id = nd && nd.data ? nd.data.parent_node : "";
|
|
59390
59821
|
if (parent_id) return node_is_compact(gobj, parent_id);
|
|
59391
|
-
return gobj_read_str_attr(gobj, "node_mode")
|
|
59822
|
+
return gobj_read_str_attr(gobj, "node_mode") !== "expanded";
|
|
59392
59823
|
}
|
|
59393
59824
|
function more_chip_style(gobj, nd, color, rest) {
|
|
59394
59825
|
let compact = more_chip_is_compact(gobj, nd);
|
|
@@ -59847,6 +60278,7 @@ async function reconcile_fold_apply(gobj, opts, visible) {
|
|
|
59847
60278
|
update_edge_icon_position(gobj);
|
|
59848
60279
|
update_node_icon_position(gobj);
|
|
59849
60280
|
update_link_icon_position(gobj);
|
|
60281
|
+
update_port_icon_position(gobj);
|
|
59850
60282
|
return changed;
|
|
59851
60283
|
}
|
|
59852
60284
|
/************************************************************
|
|
@@ -60438,9 +60870,9 @@ function ac_set_loose_topics(gobj, event, kw, src) {
|
|
|
60438
60870
|
* and lays the graph out again, because a square and a card
|
|
60439
60871
|
* do not occupy the same room.
|
|
60440
60872
|
************************************************************/
|
|
60441
|
-
function ac_set_node_mode(gobj, event, kw, src) {
|
|
60873
|
+
function ac_set_node_mode$1(gobj, event, kw, src) {
|
|
60442
60874
|
let priv = gobj.priv;
|
|
60443
|
-
let mode = kw && kw.node_mode
|
|
60875
|
+
let mode = kw && kw.node_mode && str_in_list(NODE_MODES$1, kw.node_mode) ? kw.node_mode : "expanded";
|
|
60444
60876
|
gobj_write_str_attr(gobj, "node_mode", mode);
|
|
60445
60877
|
priv._open_nodes = /* @__PURE__ */ new Set();
|
|
60446
60878
|
if (!priv.graph || !priv._fold_model) return 0;
|
|
@@ -60453,15 +60885,15 @@ function ac_set_node_mode(gobj, event, kw, src) {
|
|
|
60453
60885
|
return 0;
|
|
60454
60886
|
}
|
|
60455
60887
|
/************************************************************
|
|
60456
|
-
* The name under a
|
|
60457
|
-
*
|
|
60458
|
-
*
|
|
60888
|
+
* The name under a figure, on or off. Only the `shape` nodes
|
|
60889
|
+
* change, and nothing moves: the label hangs outside the figure
|
|
60890
|
+
* and the layout measures the figure.
|
|
60459
60891
|
************************************************************/
|
|
60460
60892
|
function ac_set_node_labels(gobj, event, kw, src) {
|
|
60461
60893
|
let priv = gobj.priv;
|
|
60462
60894
|
gobj_write_bool_attr(gobj, "node_labels", !!(kw && kw.node_labels));
|
|
60463
60895
|
if (!priv.graph) return 0;
|
|
60464
|
-
reshape_nodes(gobj, all_record_node_ids(gobj).filter((id) =>
|
|
60896
|
+
reshape_nodes(gobj, all_record_node_ids(gobj).filter((id) => node_mode_of(gobj, id) === "shape"));
|
|
60465
60897
|
return 0;
|
|
60466
60898
|
}
|
|
60467
60899
|
/************************************************************
|
|
@@ -60469,7 +60901,7 @@ function ac_set_node_labels(gobj, event, kw, src) {
|
|
|
60469
60901
|
* or the context menu). It holds still on screen while the
|
|
60470
60902
|
* rest of the graph makes room, as a fold does.
|
|
60471
60903
|
************************************************************/
|
|
60472
|
-
function ac_toggle_node_mode
|
|
60904
|
+
function ac_toggle_node_mode(gobj, event, kw, src) {
|
|
60473
60905
|
let priv = gobj.priv;
|
|
60474
60906
|
let node_id = kw && kw.id || "";
|
|
60475
60907
|
if (!priv.graph || !node_id) {
|
|
@@ -60998,7 +61430,7 @@ function create_gclass$4(gclass_name) {
|
|
|
60998
61430
|
],
|
|
60999
61431
|
[
|
|
61000
61432
|
"EV_SET_NODE_MODE",
|
|
61001
|
-
ac_set_node_mode,
|
|
61433
|
+
ac_set_node_mode$1,
|
|
61002
61434
|
null
|
|
61003
61435
|
],
|
|
61004
61436
|
[
|
|
@@ -61008,7 +61440,7 @@ function create_gclass$4(gclass_name) {
|
|
|
61008
61440
|
],
|
|
61009
61441
|
[
|
|
61010
61442
|
"EV_TOGGLE_NODE_MODE",
|
|
61011
|
-
ac_toggle_node_mode
|
|
61443
|
+
ac_toggle_node_mode,
|
|
61012
61444
|
null
|
|
61013
61445
|
],
|
|
61014
61446
|
[
|
|
@@ -61189,8 +61621,8 @@ var attrs_table$3 = [
|
|
|
61189
61621
|
SDATA(data_type_t.DTP_LIST, "hidden_topics", sdata_flag_t.SDF_PERSIST, "[]", "Topics hidden from the graph (legend). User preference, per treedb"),
|
|
61190
61622
|
SDATA(data_type_t.DTP_STRING, "main_topic", sdata_flag_t.SDF_PERSIST, "", "The topic the tree hangs from; empty = deduced by the graph. User preference, per treedb"),
|
|
61191
61623
|
SDATA(data_type_t.DTP_LIST, "loose_topics", sdata_flag_t.SDF_PERSIST, "[]", "Topics whose LOOSE records (no parent) are shown. User preference, per treedb"),
|
|
61192
|
-
SDATA(data_type_t.DTP_STRING, "node_mode", sdata_flag_t.SDF_PERSIST, "expanded", "How the records are drawn: `expanded` = the cards with their ports, `compact` = coloured
|
|
61193
|
-
SDATA(data_type_t.DTP_BOOLEAN, "node_labels", sdata_flag_t.SDF_PERSIST, true, "A
|
|
61624
|
+
SDATA(data_type_t.DTP_STRING, "node_mode", sdata_flag_t.SDF_PERSIST, "expanded", "How the records are drawn: `expanded` = the cards with their pills and ports, `compact` = one-line pills with the name, `shape` = coloured figures, the topology alone. User preference"),
|
|
61625
|
+
SDATA(data_type_t.DTP_BOOLEAN, "node_labels", sdata_flag_t.SDF_PERSIST, true, "A `shape` node says its name under its figure. User preference"),
|
|
61194
61626
|
SDATA(data_type_t.DTP_POINTER, "gobj_remote_yuno", 0, null, "Remote Yuno to request data"),
|
|
61195
61627
|
SDATA(data_type_t.DTP_STRING, "treedb_name", 0, null, "Remote service treedb name"),
|
|
61196
61628
|
SDATA(data_type_t.DTP_DICT, "descs", 0, null, "Descriptions of topics obtained"),
|
|
@@ -61474,44 +61906,92 @@ function option_label(name) {
|
|
|
61474
61906
|
* its context menu (the child's business).
|
|
61475
61907
|
************************************************************/
|
|
61476
61908
|
function node_shape_items(gobj, wide) {
|
|
61477
|
-
let
|
|
61478
|
-
|
|
61909
|
+
let options = NODE_MODES.map((mode) => [
|
|
61910
|
+
"option",
|
|
61911
|
+
{
|
|
61912
|
+
value: mode,
|
|
61913
|
+
"data-i18n": NODE_MODE_LABELS[mode]
|
|
61914
|
+
},
|
|
61915
|
+
t(NODE_MODE_LABELS[mode])
|
|
61916
|
+
]);
|
|
61917
|
+
return [
|
|
61918
|
+
[
|
|
61919
|
+
"span",
|
|
61920
|
+
{
|
|
61921
|
+
class: "GRAPH_NODE_MODE_LABEL is-hidden-mobile",
|
|
61922
|
+
style: "padding-left:10px; padding-right:5px;",
|
|
61923
|
+
i18n: "nodes"
|
|
61924
|
+
},
|
|
61925
|
+
"nodes"
|
|
61926
|
+
],
|
|
61927
|
+
[
|
|
61928
|
+
"div",
|
|
61929
|
+
{ class: "select" },
|
|
61930
|
+
[[
|
|
61931
|
+
"select",
|
|
61932
|
+
{
|
|
61933
|
+
class: "GRAPH_NODE_MODE_SELECT",
|
|
61934
|
+
title: t("nodes"),
|
|
61935
|
+
"data-i18n-title": "nodes",
|
|
61936
|
+
"aria-label": t("nodes"),
|
|
61937
|
+
"data-i18n-aria-label": "nodes"
|
|
61938
|
+
},
|
|
61939
|
+
options
|
|
61940
|
+
]],
|
|
61941
|
+
{ change: (evt) => {
|
|
61942
|
+
evt.stopPropagation();
|
|
61943
|
+
gobj_send_event(gobj, "EV_SET_NODE_MODE", { node_mode: evt.target.value }, gobj);
|
|
61944
|
+
} }
|
|
61945
|
+
],
|
|
61946
|
+
[
|
|
61479
61947
|
"button",
|
|
61480
61948
|
{
|
|
61481
|
-
class:
|
|
61949
|
+
class: "GRAPH_NODE_LABELS button",
|
|
61482
61950
|
type: "button",
|
|
61483
61951
|
style: {
|
|
61484
61952
|
height: wide,
|
|
61485
61953
|
width: "2.5em"
|
|
61486
61954
|
},
|
|
61487
|
-
title: t(
|
|
61488
|
-
"data-i18n-title":
|
|
61489
|
-
"aria-label": t(
|
|
61490
|
-
"data-i18n-aria-label":
|
|
61955
|
+
title: t("node labels"),
|
|
61956
|
+
"data-i18n-title": "node labels",
|
|
61957
|
+
"aria-label": t("node labels"),
|
|
61958
|
+
"data-i18n-aria-label": "node labels",
|
|
61491
61959
|
"aria-pressed": "false"
|
|
61492
61960
|
},
|
|
61493
61961
|
["i", {
|
|
61494
61962
|
style: "font-size:1.5em; color:inherit;",
|
|
61495
|
-
class:
|
|
61963
|
+
class: "yi-font"
|
|
61496
61964
|
}],
|
|
61497
61965
|
{ click: (evt) => {
|
|
61498
61966
|
evt.stopPropagation();
|
|
61499
|
-
gobj_send_event(gobj,
|
|
61967
|
+
gobj_send_event(gobj, "EV_TOGGLE_NODE_LABELS", {}, gobj);
|
|
61500
61968
|
} }
|
|
61501
|
-
]
|
|
61502
|
-
|
|
61503
|
-
return [toggle("GRAPH_NODE_MODE", "yi-hexagon-nodes", "EV_TOGGLE_NODE_MODE", "closed nodes"), toggle("GRAPH_NODE_LABELS", "yi-font", "EV_TOGGLE_NODE_LABELS", "node labels")];
|
|
61969
|
+
]
|
|
61970
|
+
];
|
|
61504
61971
|
}
|
|
61972
|
+
var NODE_MODES = [
|
|
61973
|
+
"expanded",
|
|
61974
|
+
"compact",
|
|
61975
|
+
"shape"
|
|
61976
|
+
];
|
|
61977
|
+
var NODE_MODE_LABELS = {
|
|
61978
|
+
expanded: "full",
|
|
61979
|
+
compact: "compact",
|
|
61980
|
+
shape: "shape"
|
|
61981
|
+
};
|
|
61505
61982
|
function refresh_node_shape_buttons(gobj, $root) {
|
|
61506
61983
|
if (!$root) return;
|
|
61507
|
-
let
|
|
61984
|
+
let mode = gobj_read_str_attr(gobj, "node_mode");
|
|
61985
|
+
if (!NODE_MODES.includes(mode)) mode = "expanded";
|
|
61508
61986
|
let labels = gobj_read_bool_attr(gobj, "node_labels");
|
|
61509
|
-
|
|
61987
|
+
let $mode = $root.querySelector(".GRAPH_NODE_MODE_SELECT");
|
|
61988
|
+
if ($mode) $mode.value = mode;
|
|
61510
61989
|
set_pressed_state($root, ".GRAPH_NODE_LABELS", labels);
|
|
61511
|
-
let $mode = $root.querySelector(".GRAPH_NODE_MODE");
|
|
61512
|
-
if ($mode) $mode.setAttribute("aria-pressed", compact ? "true" : "false");
|
|
61513
61990
|
let $labels = $root.querySelector(".GRAPH_NODE_LABELS");
|
|
61514
|
-
if ($labels)
|
|
61991
|
+
if ($labels) {
|
|
61992
|
+
$labels.setAttribute("aria-pressed", labels ? "true" : "false");
|
|
61993
|
+
$labels.disabled = mode !== "shape";
|
|
61994
|
+
}
|
|
61515
61995
|
}
|
|
61516
61996
|
function make_toolbar(gobj) {
|
|
61517
61997
|
let priv = gobj.priv;
|
|
@@ -62898,13 +63378,13 @@ function ac_collapse_all(gobj, event, kw, src) {
|
|
|
62898
63378
|
return 0;
|
|
62899
63379
|
}
|
|
62900
63380
|
/************************************************************
|
|
62901
|
-
* The
|
|
62902
|
-
*
|
|
62903
|
-
* the nodes.
|
|
63381
|
+
* The view of the nodes and the labels toggle of the toolbar:
|
|
63382
|
+
* the attr changes, persists, shows on the control, and reaches
|
|
63383
|
+
* the G6 child, which owns the nodes.
|
|
62904
63384
|
************************************************************/
|
|
62905
|
-
function
|
|
63385
|
+
function ac_set_node_mode(gobj, event, kw, src) {
|
|
62906
63386
|
let priv = gobj.priv;
|
|
62907
|
-
let mode =
|
|
63387
|
+
let mode = kw && NODE_MODES.includes(kw.node_mode) ? kw.node_mode : "expanded";
|
|
62908
63388
|
gobj_write_str_attr(gobj, "node_mode", mode);
|
|
62909
63389
|
gobj_save_persistent_attrs(gobj, "node_mode");
|
|
62910
63390
|
refresh_node_shape_buttons(gobj, priv.$container);
|
|
@@ -63135,8 +63615,8 @@ function create_gclass$3(gclass_name) {
|
|
|
63135
63615
|
null
|
|
63136
63616
|
],
|
|
63137
63617
|
[
|
|
63138
|
-
"
|
|
63139
|
-
|
|
63618
|
+
"EV_SET_NODE_MODE",
|
|
63619
|
+
ac_set_node_mode,
|
|
63140
63620
|
null
|
|
63141
63621
|
],
|
|
63142
63622
|
[
|
|
@@ -63208,7 +63688,7 @@ function create_gclass$3(gclass_name) {
|
|
|
63208
63688
|
["EV_FIND_NODES", 0],
|
|
63209
63689
|
["EV_EXPAND_ALL", 0],
|
|
63210
63690
|
["EV_COLLAPSE_ALL", 0],
|
|
63211
|
-
["
|
|
63691
|
+
["EV_SET_NODE_MODE", 0],
|
|
63212
63692
|
["EV_TOGGLE_NODE_LABELS", 0],
|
|
63213
63693
|
["EV_FIND_RESULT", 0],
|
|
63214
63694
|
["EV_LAYOUT_AUTOSET", 0],
|