-
Notifications
You must be signed in to change notification settings - Fork 0
/
intersect.py
135 lines (109 loc) · 3.96 KB
/
intersect.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
import numpy as np
from numpy import linalg
import logging as log
MIN_ANGLE_TO_INTERSECT = 20 * 100
def calculate_extern(hori, vert=None):
log.debug("calculating external intersections between groups of lines...")
if vert is None:
log.debug("-> calculating all intersections in the same group")
vert = hori
if hori is None:
log.debug("-> line group is empty, returning None.")
return None
rows = []
for i in range(l0 := hori.shape[0]):
x0, y0, x1, y1, r, t = hori[i]
column = []
for j in range(l1 := vert.shape[0]):
xx0, yy0, xx1, yy1, rr, tt = vert[j]
if 0 != i != (l0 - 1) and 0 != j != (l1 - 1):
column.append((30000, 30000))
continue
if (x0, y0, x1, x1) == (xx0, yy0, xx1, yy1):
continue
dtheta = abs(t - tt)
tol0 = MIN_ANGLE_TO_INTERSECT
tol1 = 180*100 - tol0
if (dtheta < tol0 or dtheta > tol1):
continue
xdiff = (x0 - x1, xx0 - xx1)
ydiff = (y0 - y1, yy0 - yy1)
div = linalg.det([xdiff, ydiff])
if div == 0:
continue
d = (linalg.det([(x0, y0), (x1, y1)]),
linalg.det([(xx0, yy0), (xx1, yy1)]))
x = linalg.det([d, xdiff]) / div
y = linalg.det([d, ydiff]) / div
column.append((x, y))
rows.append(column)
try:
inter = np.round(rows)
return np.array(inter, dtype='int32')
except Exception:
return None
def calculate_all(lines0, lines1=None, onlylast=False, limit=False):
if lines1 is None:
lines1 = lines0
max_x0 = np.max([lines0[:, 0], lines0[:, 2]])
max_x1 = np.max([lines1[:, 0], lines1[:, 2]])
max_y0 = np.max([lines0[:, 1], lines0[:, 3]])
max_y1 = np.max([lines1[:, 1], lines1[:, 3]])
max_x = max(max_x0, max_x1)
max_y = max(max_y0, max_y1)
rows = []
for line0 in lines0:
x0, y0, x1, y1, r, t = line0
col = []
for line1 in lines1:
xx0, yy0, xx1, yy1, rr, tt = line1
if (x0, y0, x1, x1) == (xx0, yy0, xx1, yy1):
continue
if not limit:
dtheta = abs(t - tt)
tol0 = MIN_ANGLE_TO_INTERSECT
tol1 = 180*100 - tol0
if (dtheta < tol0 or dtheta > tol1):
continue
xdiff = (x0 - x1, xx0 - xx1)
ydiff = (y0 - y1, yy0 - yy1)
div = linalg.det([xdiff, ydiff])
if div == 0:
continue
d = (linalg.det([(x0, y0), (x1, y1)]),
linalg.det([(xx0, yy0), (xx1, yy1)]))
x = linalg.det([d, xdiff]) / div
y = linalg.det([d, ydiff]) / div
if limit:
if x < 0 or x > max_x or y < 0 or y > max_y:
continue
col.append((x, y))
rows.append(col)
inter = np.round(rows)
return np.array(inter, dtype='int32')
def calculate_single(line0, canny, kind=0):
match kind:
case 0:
line1 = (50, 0, 400, 0, 0, 0)
case 1:
line1 = (0, 50, 0, 400, 0, 0)
case 2:
line1 = (50, canny.shape[0], 400, canny.shape[0], 0, 0)
case 3:
line1 = (canny.shape[1], 50, canny.shape[1], 400, 0, 0)
x0, y0, x1, y1 = line0[:4]
xx0, yy0, xx1, yy1 = line1[:4]
if (x0, y0, x1, x1) == (xx0, yy0, xx1, yy1):
log.warning("lines should not be equal")
return (30000, 30000)
xdiff = (x0 - x1, xx0 - xx1)
ydiff = (y0 - y1, yy0 - yy1)
div = linalg.det([xdiff, ydiff])
if div == 0:
log.debug("div == 0 (parallel lines)")
return (30000, 30000)
d = (linalg.det([(x0, y0), (x1, y1)]),
linalg.det([(xx0, yy0), (xx1, yy1)]))
x = round(linalg.det([d, xdiff]) / div)
y = round(linalg.det([d, ydiff]) / div)
return np.array((x, y), dtype='int32')