Passed
Push — master ( b9ad79...37a8a1 )
by Pawel
03:04
created

graph-links.ts ➔ createLinkPath   B

Complexity

Conditions 6

Size

Total Lines 43
Code Lines 40

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
eloc 40
dl 0
loc 43
rs 7.9866
c 0
b 0
f 0
cc 6
1
import { DependencyLink, NodeSelection } from '../components/types';
2
import { ElementIds, Colors } from '../utils/AppConsts';
3
import { select } from 'd3-selection';
4
import { getNodeDimensions } from './graph-nodes';
5
6
export function createLinks(zoomLayer: NodeSelection<SVGGElement>, links: DependencyLink[]) {
7
    return zoomLayer
8
        .append('g')
9
        .attr('id', ElementIds.LINKS)
10
        .lower()
11
        .selectAll<HTMLElement, DependencyLink>('line.link')
12
        .data(links)
13
        .enter()
14
        .append<SVGPathElement>('svg:path')
15
        .attr('class', 'link')
16
        .attr('marker-end', 'url(#provider)')
17
        .style('stroke-width', 1);
18
}
19
20
export function createLinkMarkersDefinition(svgContainer: any): void {
21
    svgContainer
22
        .append('svg:defs')
23
        .append('svg:marker')
24
        .attr('id', 'provider')
25
        .attr('viewBox', '-5 -5 40 10')
26
        .attr('refX', 15)
27
        .attr('refY', 0)
28
        .attr('markerWidth', 40)
29
        .attr('markerHeight', 40)
30
        .attr('orient', 'auto')
31
        .append('svg:path')
32
        .attr('d', 'M0,-5L20,0L0,5,q10 -5,0 -10')
33
        .attr('fill', '#dcdee0');
34
}
35
36
export function createLinkPath(this: Element, link: DependencyLink): void {
37
    if (!link.source.x || !link.source.y || !link.target.x || !link.target.y) {
38
        return;
39
    }
40
41
    const xDiff = link.source.x - link.target.x;
42
    const yDiff = link.source.y - link.target.y;
43
44
    const isSourceOnTheLeft = xDiff < 0;
45
    const isSourceBelowTarget = yDiff > 0;
46
47
    const angleInRadians = Math.abs(Math.atan(yDiff / xDiff));
48
    const cosinus = Math.cos(angleInRadians);
49
    const sinus = Math.sin(angleInRadians);
50
51
    const offsetY = 50 * sinus;
52
    const offsetYBelow = -offsetY - 5;
53
54
    const sourceLabelWidth = getNodeDimensions(link.source).width;
55
    link.source.width = sourceLabelWidth;
56
    const targetLabelWidth = getNodeDimensions(link.target).width;
57
    link.target.width = targetLabelWidth;
58
59
    const sourceNewX = isSourceOnTheLeft ? (sourceLabelWidth / 2 + 15) * cosinus : (-sourceLabelWidth / 2 - 15) * cosinus;
60
    const sourceNewY = isSourceBelowTarget ? offsetYBelow : offsetY;
61
62
    const targetNewX = isSourceOnTheLeft ? (-targetLabelWidth / 2 - 15) * cosinus : (targetLabelWidth / 2 + 15) * cosinus;
63
    const targetNewY = isSourceBelowTarget ? offsetY : offsetYBelow;
64
65
    select<Element, DependencyLink>(this)
66
        .attr(
67
            'd',
68
            'M' +
69
                (link.source.x + sourceNewX) +
70
                ',' +
71
                (link.source.y + sourceNewY) +
72
                ', ' +
73
                (link.target.x + targetNewX) +
74
                ',' +
75
                (link.target.y + targetNewY)
76
        )
77
        .attr('stroke', Colors.LIGHT_GREY);
78
}
79