forked from hyoo-ru/mam_mol
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathdot.view.ts
82 lines (65 loc) · 2 KB
/
dot.view.ts
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
namespace $.$$ {
export class $mol_plot_dot extends $.$mol_plot_dot {
@$mol_mem
filled(): Set<number> {
return new Set()
}
@ $mol_mem
indexes() {
const radius = this.diameter() / 2
// calculate by cpu
const points_max = this.points_max()
const viewport = this.viewport()
const viewport_left = viewport.x.min - radius
const viewport_right = viewport.x.max + radius
const viewport_bottom = viewport.y.min - radius
const viewport_top = viewport.y.max + radius
const [shift_x, shift_y] = this.shift()
const [scale_x, scale_y] = this.scale()
let last_x = Number.NEGATIVE_INFINITY
let last_y = Number.NEGATIVE_INFINITY
let spacing = 0
let filled: Set<number> = this.filled()
let indexes: number[]
const series_x = this.series_x()
const series_y = this.series_y()
do {
indexes = []
for (let i = 0; i < series_x.length; i++) {
const point_x = series_x[i]
const point_y = series_y[i]
const scaled_x = Math.round(shift_x + point_x * scale_x)
const scaled_y = Math.round(shift_y + point_y * scale_y)
if (
Math.abs( scaled_x - last_x ) < radius
&& Math.abs( scaled_y - last_y ) < radius
) continue
last_x = scaled_x
last_y = scaled_y
if (scaled_x < viewport_left) continue
if (scaled_y < viewport_bottom) continue
if (scaled_x > viewport_right) continue
if (scaled_y > viewport_top) continue
if (spacing !== 0) {
const key = $mol_coord_pack(
Math.round(point_x * scale_x / spacing) * spacing,
Math.round(point_y * scale_y / spacing) * spacing
)
if (filled.has(key)) continue
filled.add(key)
}
indexes.push(i)
if (indexes.length > points_max) break
}
spacing += Math.ceil(radius)
filled.clear()
} while (indexes.length > points_max)
return indexes
}
curve() {
const points = this.points()
if( points.length === 0 ) return ''
return points.map( point => `M ${point.join(' ')} v 0`).join( ' ' )
}
}
}