graflow: port heights used in layer reordering
This commit is contained in:
52
bzGraflow.js
52
bzGraflow.js
@@ -59,11 +59,6 @@ class BZgraflow extends Buildoz{
|
|||||||
}
|
}
|
||||||
await this.loadNodes(flowObj.nodesFile)
|
await this.loadNodes(flowObj.nodesFile)
|
||||||
this.flow = flowObj.flow
|
this.flow = flowObj.flow
|
||||||
|
|
||||||
if(this.hasAnyLoop()) {
|
|
||||||
console.warn('This flow has loops.Optimization not available')
|
|
||||||
console.log('===Loops:===>', this.getLoopingLinks())
|
|
||||||
}
|
|
||||||
this.refresh()
|
this.refresh()
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -198,7 +193,6 @@ class BZgraflow extends Buildoz{
|
|||||||
if(this.hasAnyLoop(this.flow.nodes, this.flow.links)){
|
if(this.hasAnyLoop(this.flow.nodes, this.flow.links)){
|
||||||
console.warn('Loop(s) detected... Cannot auto-place !')
|
console.warn('Loop(s) detected... Cannot auto-place !')
|
||||||
const backEdges = this.findBackEdges(this.flow.nodes, this.flow.links)
|
const backEdges = this.findBackEdges(this.flow.nodes, this.flow.links)
|
||||||
console.log('===BackEdges:===>', backEdges)
|
|
||||||
linksWithoutBackEdges = this.flow.links.filter((link, idx) => (!backEdges.includes(idx)) && (link.from[0] != link.to[0]))
|
linksWithoutBackEdges = this.flow.links.filter((link, idx) => (!backEdges.includes(idx)) && (link.from[0] != link.to[0]))
|
||||||
} else {
|
} else {
|
||||||
linksWithoutBackEdges = this.flow.links
|
linksWithoutBackEdges = this.flow.links
|
||||||
@@ -221,14 +215,14 @@ class BZgraflow extends Buildoz{
|
|||||||
const layers = this.computeLayers(this.flow.nodes, parents)
|
const layers = this.computeLayers(this.flow.nodes, parents)
|
||||||
let maxHeight = 0; let maxWidth = 0
|
let maxHeight = 0; let maxWidth = 0
|
||||||
const layerHeights = []; const layerWidths = [];
|
const layerHeights = []; const layerWidths = [];
|
||||||
const indexes = {} // Todo: a
|
const indexes = {} // indexes[nid] = { base: <int>, ports: { [portId]: <float in [0,1)> } }
|
||||||
for(const layer of layers){
|
for(const layer of layers){
|
||||||
let totHeight = 0; let totWidth = 0
|
let totHeight = 0; let totWidth = 0
|
||||||
for(const [idx, nid] of layer.entries()){
|
for(const [idx, nid] of layer.entries()){
|
||||||
const bb = this.stagedNodes[nid].getBoundingClientRect()
|
const bb = this.stagedNodes[nid].getBoundingClientRect()
|
||||||
totHeight += bb.height + gapy
|
totHeight += bb.height + gapy
|
||||||
totWidth += bb.width + gapx
|
totWidth += bb.width + gapx
|
||||||
indexes[nid] = idx
|
indexes[nid] = { base: idx, ports: this.computePortOffsets(nid, orientation) }
|
||||||
}
|
}
|
||||||
if(totHeight>maxHeight) maxHeight = totHeight
|
if(totHeight>maxHeight) maxHeight = totHeight
|
||||||
layerHeights.push(totHeight)
|
layerHeights.push(totHeight)
|
||||||
@@ -236,7 +230,7 @@ class BZgraflow extends Buildoz{
|
|||||||
layerWidths.push(totWidth)
|
layerWidths.push(totWidth)
|
||||||
}
|
}
|
||||||
|
|
||||||
this.reorderLayers(layers, parents, indexes)
|
this.reorderLayers(layers, parents, indexes, orientation)
|
||||||
|
|
||||||
if(orientation=='horizontal'){
|
if(orientation=='horizontal'){
|
||||||
let x = gapx
|
let x = gapx
|
||||||
@@ -263,17 +257,45 @@ class BZgraflow extends Buildoz{
|
|||||||
x += gapx + bb.width
|
x += gapx + bb.width
|
||||||
}
|
}
|
||||||
y += hMax + gapy
|
y += hMax + gapy
|
||||||
console.log(y, hMax, gapy )
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
reorderLayers(layers, parents, indexes){
|
computePortOffsets(nid, orientation = 'horizontal'){
|
||||||
|
const node = this.stagedNodes[nid]
|
||||||
|
if(!node || !node.ports) return({})
|
||||||
|
const axis = (orientation === 'vertical') ? 'x' : 'y'
|
||||||
|
const nodeRect = node.getBoundingClientRect()
|
||||||
|
const ports = Object.entries(node.ports)
|
||||||
|
.map(([pid, p]) => {
|
||||||
|
const r = p.el.getBoundingClientRect()
|
||||||
|
const pos = (axis === 'x')
|
||||||
|
? (r.left + (r.width / 2) - nodeRect.left)
|
||||||
|
: (r.top + (r.height / 2) - nodeRect.top)
|
||||||
|
return({ pid, pos })
|
||||||
|
})
|
||||||
|
.sort((a, b) => a.pos - b.pos) // smaller pos => "higher/left" => smaller offset
|
||||||
|
|
||||||
|
const denom = ports.length + 1
|
||||||
|
const offsets = {}
|
||||||
|
for(const [rank, item] of ports.entries()){
|
||||||
|
offsets[item.pid] = rank / denom // always < 1
|
||||||
|
}
|
||||||
|
return(offsets)
|
||||||
|
}
|
||||||
|
|
||||||
|
reorderLayers(layers, parents, indexes, orientation = 'horizontal'){
|
||||||
const swap = (vect, todo) => {
|
const swap = (vect, todo) => {
|
||||||
for(const s of todo){
|
for(const s of todo){
|
||||||
[vect[s[0]], vect[s[1]]] = [vect[s[1]], vect[s[0]]]
|
[vect[s[0]], vect[s[1]]] = [vect[s[1]], vect[s[0]]]
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
const adjIndex = (nid, portId) => {
|
||||||
|
const info = indexes?.[nid]
|
||||||
|
const base = (info && info.base !== undefined) ? info.base : 0
|
||||||
|
const off = (portId && info?.ports?.[portId] !== undefined) ? info.ports[portId] : 0
|
||||||
|
return(base + off)
|
||||||
|
}
|
||||||
for(const [lidx, layer] of layers.entries()){
|
for(const [lidx, layer] of layers.entries()){
|
||||||
if(lidx==0) continue
|
if(lidx==0) continue
|
||||||
const toSwap = []
|
const toSwap = []
|
||||||
@@ -284,7 +306,13 @@ class BZgraflow extends Buildoz{
|
|||||||
for(let j=i+1; j<layer.length; j++){
|
for(let j=i+1; j<layer.length; j++){
|
||||||
const nid2 = layer[j]
|
const nid2 = layer[j]
|
||||||
const pnid2 = parents[nid2].find((nid => layers[lidx-1].includes(nid)))
|
const pnid2 = parents[nid2].find((nid => layers[lidx-1].includes(nid)))
|
||||||
if(((indexes[pnid1] - indexes[pnid2]) * (indexes[nid1] - indexes[nid2])) < 0) { // crossing !
|
const link1 = (pnid1) ? this.getLink(pnid1, nid1) : null
|
||||||
|
const link2 = (pnid2) ? this.getLink(pnid2, nid2) : null
|
||||||
|
const p1 = adjIndex(pnid1, link1?.from?.[1])
|
||||||
|
const p2 = adjIndex(pnid2, link2?.from?.[1])
|
||||||
|
const c1 = adjIndex(nid1, link1?.to?.[1])
|
||||||
|
const c2 = adjIndex(nid2, link2?.to?.[1])
|
||||||
|
if(((p1 - p2) * (c1 - c2)) < 0) { // crossing (now refined by per-port ordering)
|
||||||
toSwap.push([i, j])
|
toSwap.push([i, j])
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user