@cosmos.gl/graph 2.6.0 → 2.6.2-rc.0
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/dist/config.d.ts +3 -0
- package/dist/index.d.ts +48 -6
- package/dist/index.js +1346 -1289
- package/dist/index.js.map +1 -1
- package/dist/index.min.js +15 -15
- package/dist/index.min.js.map +1 -1
- package/package.json +5 -1
- package/.eslintrc +0 -147
- package/.github/SECURITY.md +0 -19
- package/.github/dco.yml +0 -4
- package/.github/workflows/github_pages.yml +0 -54
- package/.storybook/main.ts +0 -26
- package/.storybook/manager-head.html +0 -1
- package/.storybook/manager.ts +0 -14
- package/.storybook/preview.ts +0 -29
- package/.storybook/style.css +0 -3
- package/CHARTER.md +0 -69
- package/CODE_OF_CONDUCT.md +0 -178
- package/CONTRIBUTING.md +0 -22
- package/GOVERNANCE.md +0 -21
- package/cosmos-2-0-migration-notes.md +0 -98
- package/cosmos_awesome.md +0 -96
- package/dist/stories/beginners/basic-set-up/data-gen.d.ts +0 -4
- package/dist/stories/beginners/basic-set-up/index.d.ts +0 -5
- package/dist/stories/beginners/link-hovering/data-generator.d.ts +0 -19
- package/dist/stories/beginners/link-hovering/index.d.ts +0 -5
- package/dist/stories/beginners/pinned-points/data-gen.d.ts +0 -5
- package/dist/stories/beginners/pinned-points/index.d.ts +0 -5
- package/dist/stories/beginners/point-labels/data.d.ts +0 -13
- package/dist/stories/beginners/point-labels/index.d.ts +0 -9
- package/dist/stories/beginners/point-labels/labels.d.ts +0 -8
- package/dist/stories/beginners/quick-start.d.ts +0 -5
- package/dist/stories/beginners/remove-points/config.d.ts +0 -2
- package/dist/stories/beginners/remove-points/data-gen.d.ts +0 -4
- package/dist/stories/beginners/remove-points/index.d.ts +0 -5
- package/dist/stories/beginners.stories.d.ts +0 -11
- package/dist/stories/clusters/polygon-selection/index.d.ts +0 -6
- package/dist/stories/clusters/polygon-selection/polygon.d.ts +0 -20
- package/dist/stories/clusters/radial.d.ts +0 -5
- package/dist/stories/clusters/with-labels.d.ts +0 -6
- package/dist/stories/clusters/worm.d.ts +0 -5
- package/dist/stories/clusters.stories.d.ts +0 -9
- package/dist/stories/create-cluster-labels.d.ts +0 -4
- package/dist/stories/create-cosmos.d.ts +0 -16
- package/dist/stories/create-story.d.ts +0 -16
- package/dist/stories/experiments/full-mesh.d.ts +0 -5
- package/dist/stories/experiments/mesh-with-holes.d.ts +0 -5
- package/dist/stories/experiments.stories.d.ts +0 -7
- package/dist/stories/generate-mesh-data.d.ts +0 -12
- package/dist/stories/geospatial/moscow-metro-stations/index.d.ts +0 -15
- package/dist/stories/geospatial/moscow-metro-stations/moscow-metro-coords.d.ts +0 -1
- package/dist/stories/geospatial/moscow-metro-stations/point-colors.d.ts +0 -1
- package/dist/stories/geospatial.stories.d.ts +0 -6
- package/dist/stories/shapes/all-shapes/index.d.ts +0 -5
- package/dist/stories/shapes/image-example/index.d.ts +0 -5
- package/dist/stories/shapes.stories.d.ts +0 -7
- package/logo.svg +0 -3
- package/rollup.config.js +0 -70
- package/src/config.ts +0 -734
- package/src/declaration.d.ts +0 -12
- package/src/graph/utils/error-message.ts +0 -23
- package/src/helper.ts +0 -74
- package/src/index.ts +0 -1635
- package/src/modules/Clusters/calculate-centermass.frag +0 -9
- package/src/modules/Clusters/calculate-centermass.vert +0 -26
- package/src/modules/Clusters/force-cluster.frag +0 -39
- package/src/modules/Clusters/index.ts +0 -200
- package/src/modules/Drag/index.ts +0 -33
- package/src/modules/FPSMonitor/css.ts +0 -53
- package/src/modules/FPSMonitor/index.ts +0 -28
- package/src/modules/ForceCenter/calculate-centermass.frag +0 -9
- package/src/modules/ForceCenter/calculate-centermass.vert +0 -18
- package/src/modules/ForceCenter/force-center.frag +0 -27
- package/src/modules/ForceCenter/index.ts +0 -104
- package/src/modules/ForceGravity/force-gravity.frag +0 -27
- package/src/modules/ForceGravity/index.ts +0 -33
- package/src/modules/ForceLink/force-spring.ts +0 -73
- package/src/modules/ForceLink/index.ts +0 -149
- package/src/modules/ForceManyBody/calculate-level.frag +0 -9
- package/src/modules/ForceManyBody/calculate-level.vert +0 -25
- package/src/modules/ForceManyBody/force-centermass.frag +0 -52
- package/src/modules/ForceManyBody/force-level.frag +0 -121
- package/src/modules/ForceManyBody/index.ts +0 -223
- package/src/modules/ForceManyBody/quadtree-frag-shader.ts +0 -90
- package/src/modules/ForceManyBodyQuadtree/calculate-level.frag +0 -9
- package/src/modules/ForceManyBodyQuadtree/calculate-level.vert +0 -25
- package/src/modules/ForceManyBodyQuadtree/index.ts +0 -157
- package/src/modules/ForceManyBodyQuadtree/quadtree-frag-shader.ts +0 -93
- package/src/modules/ForceMouse/force-mouse.frag +0 -24
- package/src/modules/ForceMouse/index.ts +0 -32
- package/src/modules/GraphData/index.ts +0 -384
- package/src/modules/Lines/draw-curve-line.frag +0 -46
- package/src/modules/Lines/draw-curve-line.vert +0 -194
- package/src/modules/Lines/geometry.ts +0 -18
- package/src/modules/Lines/hovered-line-index.frag +0 -27
- package/src/modules/Lines/hovered-line-index.vert +0 -8
- package/src/modules/Lines/index.ts +0 -273
- package/src/modules/Points/atlas-utils.ts +0 -137
- package/src/modules/Points/drag-point.frag +0 -20
- package/src/modules/Points/draw-highlighted.frag +0 -16
- package/src/modules/Points/draw-highlighted.vert +0 -86
- package/src/modules/Points/draw-points.frag +0 -243
- package/src/modules/Points/draw-points.vert +0 -127
- package/src/modules/Points/fill-sampled-points.frag +0 -9
- package/src/modules/Points/fill-sampled-points.vert +0 -29
- package/src/modules/Points/find-hovered-point.frag +0 -9
- package/src/modules/Points/find-hovered-point.vert +0 -57
- package/src/modules/Points/find-points-on-area-selection.frag +0 -48
- package/src/modules/Points/find-points-on-polygon-selection.frag +0 -65
- package/src/modules/Points/index.ts +0 -968
- package/src/modules/Points/track-positions.frag +0 -18
- package/src/modules/Points/update-position.frag +0 -37
- package/src/modules/Shared/buffer.ts +0 -37
- package/src/modules/Shared/clear.frag +0 -7
- package/src/modules/Shared/quad.vert +0 -12
- package/src/modules/Store/index.ts +0 -173
- package/src/modules/Zoom/index.ts +0 -148
- package/src/modules/core-module.ts +0 -28
- package/src/stories/1. welcome.mdx +0 -81
- package/src/stories/2. configuration.mdx +0 -113
- package/src/stories/3. api-reference.mdx +0 -591
- package/src/stories/beginners/basic-set-up/data-gen.ts +0 -33
- package/src/stories/beginners/basic-set-up/index.ts +0 -163
- package/src/stories/beginners/basic-set-up/style.css +0 -35
- package/src/stories/beginners/link-hovering/data-generator.ts +0 -198
- package/src/stories/beginners/link-hovering/index.ts +0 -61
- package/src/stories/beginners/link-hovering/style.css +0 -73
- package/src/stories/beginners/pinned-points/data-gen.ts +0 -153
- package/src/stories/beginners/pinned-points/index.ts +0 -61
- package/src/stories/beginners/point-labels/data.ts +0 -73
- package/src/stories/beginners/point-labels/index.ts +0 -65
- package/src/stories/beginners/point-labels/labels.ts +0 -46
- package/src/stories/beginners/point-labels/style.css +0 -16
- package/src/stories/beginners/quick-start.ts +0 -50
- package/src/stories/beginners/remove-points/config.ts +0 -25
- package/src/stories/beginners/remove-points/data-gen.ts +0 -30
- package/src/stories/beginners/remove-points/index.ts +0 -92
- package/src/stories/beginners/remove-points/style.css +0 -31
- package/src/stories/beginners.stories.ts +0 -131
- package/src/stories/clusters/polygon-selection/index.ts +0 -51
- package/src/stories/clusters/polygon-selection/polygon.ts +0 -143
- package/src/stories/clusters/polygon-selection/style.css +0 -8
- package/src/stories/clusters/radial.ts +0 -24
- package/src/stories/clusters/with-labels.ts +0 -53
- package/src/stories/clusters/worm.ts +0 -40
- package/src/stories/clusters.stories.ts +0 -77
- package/src/stories/create-cluster-labels.ts +0 -50
- package/src/stories/create-cosmos.ts +0 -68
- package/src/stories/create-story.ts +0 -51
- package/src/stories/experiments/full-mesh.ts +0 -13
- package/src/stories/experiments/mesh-with-holes.ts +0 -13
- package/src/stories/experiments.stories.ts +0 -43
- package/src/stories/generate-mesh-data.ts +0 -125
- package/src/stories/geospatial/moscow-metro-stations/index.ts +0 -62
- package/src/stories/geospatial/moscow-metro-stations/moscow-metro-coords.ts +0 -1
- package/src/stories/geospatial/moscow-metro-stations/point-colors.ts +0 -46
- package/src/stories/geospatial/moscow-metro-stations/style.css +0 -30
- package/src/stories/geospatial.stories.ts +0 -30
- package/src/stories/shapes/all-shapes/index.ts +0 -69
- package/src/stories/shapes/image-example/icons/box.png +0 -0
- package/src/stories/shapes/image-example/icons/lego.png +0 -0
- package/src/stories/shapes/image-example/icons/s.png +0 -0
- package/src/stories/shapes/image-example/icons/swift.png +0 -0
- package/src/stories/shapes/image-example/icons/toolbox.png +0 -0
- package/src/stories/shapes/image-example/index.ts +0 -238
- package/src/stories/shapes.stories.ts +0 -37
- package/src/variables.ts +0 -68
- package/tsconfig.json +0 -41
- package/vite.config.ts +0 -54
|
@@ -1,384 +0,0 @@
|
|
|
1
|
-
import { getRgbaColor, isNumber } from '@/graph/helper'
|
|
2
|
-
import { GraphConfig } from '@/graph/config'
|
|
3
|
-
|
|
4
|
-
export enum PointShape {
|
|
5
|
-
Circle = 0,
|
|
6
|
-
Square = 1,
|
|
7
|
-
Triangle = 2,
|
|
8
|
-
Diamond = 3,
|
|
9
|
-
Pentagon = 4,
|
|
10
|
-
Hexagon = 5,
|
|
11
|
-
Star = 6,
|
|
12
|
-
Cross = 7,
|
|
13
|
-
None = 8
|
|
14
|
-
}
|
|
15
|
-
|
|
16
|
-
export class GraphData {
|
|
17
|
-
public inputPointPositions: Float32Array | undefined
|
|
18
|
-
public inputPointColors: Float32Array | undefined
|
|
19
|
-
public inputPointSizes: Float32Array | undefined
|
|
20
|
-
public inputPointShapes: Float32Array | undefined
|
|
21
|
-
public inputImageData: ImageData[] | undefined
|
|
22
|
-
public inputPointImageIndices: Float32Array | undefined
|
|
23
|
-
public inputPointImageSizes: Float32Array | undefined
|
|
24
|
-
public inputLinkColors: Float32Array | undefined
|
|
25
|
-
public inputLinkWidths: Float32Array | undefined
|
|
26
|
-
public inputLinkStrength: Float32Array | undefined
|
|
27
|
-
public inputPointClusters: (number | undefined)[] | undefined
|
|
28
|
-
public inputClusterPositions: (number | undefined)[] | undefined
|
|
29
|
-
public inputClusterStrength: Float32Array | undefined
|
|
30
|
-
public inputPinnedPoints: number[] | undefined
|
|
31
|
-
|
|
32
|
-
public pointPositions: Float32Array | undefined
|
|
33
|
-
public pointColors: Float32Array | undefined
|
|
34
|
-
public pointSizes: Float32Array | undefined
|
|
35
|
-
public pointShapes: Float32Array | undefined
|
|
36
|
-
public pointImageIndices: Float32Array | undefined
|
|
37
|
-
public pointImageSizes: Float32Array | undefined
|
|
38
|
-
|
|
39
|
-
public inputLinks: Float32Array | undefined
|
|
40
|
-
public links: Float32Array | undefined
|
|
41
|
-
public linkColors: Float32Array | undefined
|
|
42
|
-
public linkWidths: Float32Array | undefined
|
|
43
|
-
public linkArrowsBoolean: boolean[] | undefined
|
|
44
|
-
public linkArrows: number[] | undefined
|
|
45
|
-
public linkStrength: Float32Array | undefined
|
|
46
|
-
|
|
47
|
-
public pointClusters: (number | undefined)[] | undefined
|
|
48
|
-
public clusterPositions: (number | undefined)[] | undefined
|
|
49
|
-
public clusterStrength: Float32Array | undefined
|
|
50
|
-
|
|
51
|
-
/**
|
|
52
|
-
* Each inner array of `sourceIndexToTargetIndices` and `targetIndexToSourceIndices` contains pairs where:
|
|
53
|
-
* - The first value is the target/source index in the point array.
|
|
54
|
-
* - The second value is the link index in the array of links.
|
|
55
|
-
*/
|
|
56
|
-
public sourceIndexToTargetIndices: ([number, number][] | undefined)[] | undefined
|
|
57
|
-
public targetIndexToSourceIndices: ([number, number][] | undefined)[] | undefined
|
|
58
|
-
|
|
59
|
-
public degree: number[] | undefined
|
|
60
|
-
public inDegree: number[] | undefined
|
|
61
|
-
public outDegree: number[] | undefined
|
|
62
|
-
|
|
63
|
-
private _config: GraphConfig
|
|
64
|
-
|
|
65
|
-
public constructor (config: GraphConfig) {
|
|
66
|
-
this._config = config
|
|
67
|
-
}
|
|
68
|
-
|
|
69
|
-
public get pointsNumber (): number | undefined {
|
|
70
|
-
return this.pointPositions && this.pointPositions.length / 2
|
|
71
|
-
}
|
|
72
|
-
|
|
73
|
-
public get linksNumber (): number | undefined {
|
|
74
|
-
return this.links && this.links.length / 2
|
|
75
|
-
}
|
|
76
|
-
|
|
77
|
-
public updatePoints (): void {
|
|
78
|
-
this.pointPositions = this.inputPointPositions
|
|
79
|
-
}
|
|
80
|
-
|
|
81
|
-
/**
|
|
82
|
-
* Updates the point colors based on the input data or default config value.
|
|
83
|
-
*/
|
|
84
|
-
public updatePointColor (): void {
|
|
85
|
-
if (this.pointsNumber === undefined) {
|
|
86
|
-
this.pointColors = undefined
|
|
87
|
-
return
|
|
88
|
-
}
|
|
89
|
-
|
|
90
|
-
// Sets point colors to default values from config if the input is missing or does not match input points number.
|
|
91
|
-
const defaultRgba = getRgbaColor(this._config.pointDefaultColor ?? this._config.pointColor)
|
|
92
|
-
if (this.inputPointColors === undefined || this.inputPointColors.length / 4 !== this.pointsNumber) {
|
|
93
|
-
this.pointColors = new Float32Array(this.pointsNumber * 4)
|
|
94
|
-
for (let i = 0; i < this.pointColors.length / 4; i++) {
|
|
95
|
-
this.pointColors[i * 4] = defaultRgba[0]
|
|
96
|
-
this.pointColors[i * 4 + 1] = defaultRgba[1]
|
|
97
|
-
this.pointColors[i * 4 + 2] = defaultRgba[2]
|
|
98
|
-
this.pointColors[i * 4 + 3] = defaultRgba[3]
|
|
99
|
-
}
|
|
100
|
-
} else {
|
|
101
|
-
this.pointColors = this.inputPointColors
|
|
102
|
-
for (let i = 0; i < this.pointColors.length / 4; i++) {
|
|
103
|
-
if (!isNumber(this.pointColors[i * 4])) this.pointColors[i * 4] = defaultRgba[0]
|
|
104
|
-
if (!isNumber(this.pointColors[i * 4 + 1])) this.pointColors[i * 4 + 1] = defaultRgba[1]
|
|
105
|
-
if (!isNumber(this.pointColors[i * 4 + 2])) this.pointColors[i * 4 + 2] = defaultRgba[2]
|
|
106
|
-
if (!isNumber(this.pointColors[i * 4 + 3])) this.pointColors[i * 4 + 3] = defaultRgba[3]
|
|
107
|
-
}
|
|
108
|
-
}
|
|
109
|
-
}
|
|
110
|
-
|
|
111
|
-
/**
|
|
112
|
-
* Updates the point sizes based on the input data or default config value.
|
|
113
|
-
*/
|
|
114
|
-
public updatePointSize (): void {
|
|
115
|
-
if (this.pointsNumber === undefined) {
|
|
116
|
-
this.pointSizes = undefined
|
|
117
|
-
return
|
|
118
|
-
}
|
|
119
|
-
|
|
120
|
-
// Sets point sizes to default values from config if the input is missing or does not match input points number.
|
|
121
|
-
if (this.inputPointSizes === undefined || this.inputPointSizes.length !== this.pointsNumber) {
|
|
122
|
-
this.pointSizes = new Float32Array(this.pointsNumber).fill(this._config.pointSize)
|
|
123
|
-
} else {
|
|
124
|
-
this.pointSizes = this.inputPointSizes
|
|
125
|
-
for (let i = 0; i < this.pointSizes.length; i++) {
|
|
126
|
-
if (!isNumber(this.pointSizes[i])) {
|
|
127
|
-
this.pointSizes[i] = this._config.pointSize
|
|
128
|
-
}
|
|
129
|
-
}
|
|
130
|
-
}
|
|
131
|
-
}
|
|
132
|
-
|
|
133
|
-
/**
|
|
134
|
-
* Updates the point shapes based on the input data or default shape.
|
|
135
|
-
* Default behavior: Circle (0).
|
|
136
|
-
* Images are rendered above shapes.
|
|
137
|
-
*/
|
|
138
|
-
public updatePointShape (): void {
|
|
139
|
-
if (this.pointsNumber === undefined) {
|
|
140
|
-
this.pointShapes = undefined
|
|
141
|
-
return
|
|
142
|
-
}
|
|
143
|
-
|
|
144
|
-
// Determine default shape: Circle
|
|
145
|
-
const defaultShape = PointShape.Circle
|
|
146
|
-
|
|
147
|
-
// Sets point shapes to default values if the input is missing or does not match input points number.
|
|
148
|
-
if (this.inputPointShapes === undefined || this.inputPointShapes.length !== this.pointsNumber) {
|
|
149
|
-
this.pointShapes = new Float32Array(this.pointsNumber).fill(defaultShape)
|
|
150
|
-
} else {
|
|
151
|
-
this.pointShapes = new Float32Array(this.inputPointShapes)
|
|
152
|
-
const pointShapes = this.pointShapes
|
|
153
|
-
for (let i = 0; i < pointShapes.length; i++) {
|
|
154
|
-
const shape = pointShapes[i]
|
|
155
|
-
if (shape == null || !isNumber(shape) || shape < 0 || shape > 8) {
|
|
156
|
-
pointShapes[i] = defaultShape
|
|
157
|
-
}
|
|
158
|
-
}
|
|
159
|
-
}
|
|
160
|
-
}
|
|
161
|
-
|
|
162
|
-
/**
|
|
163
|
-
* Updates the point image indices based on the input data or default value (-1 for no image).
|
|
164
|
-
*/
|
|
165
|
-
public updatePointImageIndices (): void {
|
|
166
|
-
if (this.pointsNumber === undefined) {
|
|
167
|
-
this.pointImageIndices = undefined
|
|
168
|
-
return
|
|
169
|
-
}
|
|
170
|
-
|
|
171
|
-
// Sets point image indices to -1 if input is missing or doesn't match points count
|
|
172
|
-
if (this.inputPointImageIndices === undefined || this.inputPointImageIndices.length !== this.pointsNumber) {
|
|
173
|
-
this.pointImageIndices = new Float32Array(this.pointsNumber).fill(-1)
|
|
174
|
-
} else {
|
|
175
|
-
const pointImageIndices = new Float32Array(this.inputPointImageIndices)
|
|
176
|
-
for (let i = 0; i < pointImageIndices.length; i++) {
|
|
177
|
-
const rawIndex = pointImageIndices[i]
|
|
178
|
-
const imageIndex = (rawIndex === undefined) ? NaN : rawIndex
|
|
179
|
-
if (!Number.isFinite(imageIndex) || imageIndex < 0) {
|
|
180
|
-
pointImageIndices[i] = -1
|
|
181
|
-
} else {
|
|
182
|
-
pointImageIndices[i] = Math.trunc(imageIndex)
|
|
183
|
-
}
|
|
184
|
-
}
|
|
185
|
-
this.pointImageIndices = pointImageIndices
|
|
186
|
-
}
|
|
187
|
-
}
|
|
188
|
-
|
|
189
|
-
/**
|
|
190
|
-
* Updates the point image sizes based on the input data or default to point sizes.
|
|
191
|
-
*/
|
|
192
|
-
public updatePointImageSizes (): void {
|
|
193
|
-
if (this.pointsNumber === undefined) {
|
|
194
|
-
this.pointImageSizes = undefined
|
|
195
|
-
return
|
|
196
|
-
}
|
|
197
|
-
|
|
198
|
-
// Sets point image sizes to point sizes if the input is missing or does not match input points number.
|
|
199
|
-
if (this.inputPointImageSizes === undefined || this.inputPointImageSizes.length !== this.pointsNumber) {
|
|
200
|
-
this.pointImageSizes = this.pointSizes ? new Float32Array(this.pointSizes) : new Float32Array(this.pointsNumber).fill(this._config.pointSize)
|
|
201
|
-
} else {
|
|
202
|
-
this.pointImageSizes = new Float32Array(this.inputPointImageSizes)
|
|
203
|
-
for (let i = 0; i < this.pointImageSizes.length; i++) {
|
|
204
|
-
if (!isNumber(this.pointImageSizes[i])) {
|
|
205
|
-
this.pointImageSizes[i] = this.pointSizes?.[i] ?? this._config.pointSize
|
|
206
|
-
}
|
|
207
|
-
}
|
|
208
|
-
}
|
|
209
|
-
}
|
|
210
|
-
|
|
211
|
-
public updateLinks (): void {
|
|
212
|
-
this.links = this.inputLinks
|
|
213
|
-
}
|
|
214
|
-
|
|
215
|
-
/**
|
|
216
|
-
* Updates the link colors based on the input data or default config value.
|
|
217
|
-
*/
|
|
218
|
-
public updateLinkColor (): void {
|
|
219
|
-
if (this.linksNumber === undefined) {
|
|
220
|
-
this.linkColors = undefined
|
|
221
|
-
return
|
|
222
|
-
}
|
|
223
|
-
|
|
224
|
-
// Sets link colors to default values from config if the input is missing or does not match input links number.
|
|
225
|
-
const defaultRgba = getRgbaColor(this._config.linkColor)
|
|
226
|
-
if (this.inputLinkColors === undefined || this.inputLinkColors.length / 4 !== this.linksNumber) {
|
|
227
|
-
this.linkColors = new Float32Array(this.linksNumber * 4)
|
|
228
|
-
|
|
229
|
-
for (let i = 0; i < this.linkColors.length / 4; i++) {
|
|
230
|
-
this.linkColors[i * 4] = defaultRgba[0]
|
|
231
|
-
this.linkColors[i * 4 + 1] = defaultRgba[1]
|
|
232
|
-
this.linkColors[i * 4 + 2] = defaultRgba[2]
|
|
233
|
-
this.linkColors[i * 4 + 3] = defaultRgba[3]
|
|
234
|
-
}
|
|
235
|
-
} else {
|
|
236
|
-
this.linkColors = this.inputLinkColors
|
|
237
|
-
for (let i = 0; i < this.linkColors.length / 4; i++) {
|
|
238
|
-
if (!isNumber(this.linkColors[i * 4])) this.linkColors[i * 4] = defaultRgba[0]
|
|
239
|
-
if (!isNumber(this.linkColors[i * 4 + 1])) this.linkColors[i * 4 + 1] = defaultRgba[1]
|
|
240
|
-
if (!isNumber(this.linkColors[i * 4 + 2])) this.linkColors[i * 4 + 2] = defaultRgba[2]
|
|
241
|
-
if (!isNumber(this.linkColors[i * 4 + 3])) this.linkColors[i * 4 + 3] = defaultRgba[3]
|
|
242
|
-
}
|
|
243
|
-
}
|
|
244
|
-
}
|
|
245
|
-
|
|
246
|
-
/**
|
|
247
|
-
* Updates the link width based on the input data or default config value.
|
|
248
|
-
*/
|
|
249
|
-
public updateLinkWidth (): void {
|
|
250
|
-
if (this.linksNumber === undefined) {
|
|
251
|
-
this.linkWidths = undefined
|
|
252
|
-
return
|
|
253
|
-
}
|
|
254
|
-
|
|
255
|
-
// Sets link widths to default values from config if the input is missing or does not match input links number.
|
|
256
|
-
if (this.inputLinkWidths === undefined || this.inputLinkWidths.length !== this.linksNumber) {
|
|
257
|
-
this.linkWidths = new Float32Array(this.linksNumber).fill(this._config.linkWidth)
|
|
258
|
-
} else {
|
|
259
|
-
this.linkWidths = this.inputLinkWidths
|
|
260
|
-
for (let i = 0; i < this.linkWidths.length; i++) {
|
|
261
|
-
if (!isNumber(this.linkWidths[i])) {
|
|
262
|
-
this.linkWidths[i] = this._config.linkWidth
|
|
263
|
-
}
|
|
264
|
-
}
|
|
265
|
-
}
|
|
266
|
-
}
|
|
267
|
-
|
|
268
|
-
/**
|
|
269
|
-
* Updates the link arrows based on the input data or default config value.
|
|
270
|
-
*/
|
|
271
|
-
public updateArrows (): void {
|
|
272
|
-
if (this.linksNumber === undefined) {
|
|
273
|
-
this.linkArrows = undefined
|
|
274
|
-
return
|
|
275
|
-
}
|
|
276
|
-
|
|
277
|
-
// Sets link arrows to default values from config if the input is missing or does not match input links number.
|
|
278
|
-
if (this.linkArrowsBoolean === undefined || this.linkArrowsBoolean.length !== this.linksNumber) {
|
|
279
|
-
this.linkArrows = new Array(this.linksNumber).fill(+this._config.linkArrows)
|
|
280
|
-
} else {
|
|
281
|
-
this.linkArrows = this.linkArrowsBoolean.map(d => +d)
|
|
282
|
-
}
|
|
283
|
-
}
|
|
284
|
-
|
|
285
|
-
public updateLinkStrength (): void {
|
|
286
|
-
if (this.linksNumber === undefined) {
|
|
287
|
-
this.linkStrength = undefined
|
|
288
|
-
}
|
|
289
|
-
|
|
290
|
-
if (this.inputLinkStrength === undefined || this.inputLinkStrength.length !== this.linksNumber) {
|
|
291
|
-
this.linkStrength = undefined
|
|
292
|
-
} else {
|
|
293
|
-
this.linkStrength = this.inputLinkStrength
|
|
294
|
-
}
|
|
295
|
-
}
|
|
296
|
-
|
|
297
|
-
public updateClusters (): void {
|
|
298
|
-
if (this.pointsNumber === undefined) {
|
|
299
|
-
this.pointClusters = undefined
|
|
300
|
-
this.clusterPositions = undefined
|
|
301
|
-
return
|
|
302
|
-
}
|
|
303
|
-
if (this.inputPointClusters === undefined || this.inputPointClusters.length !== this.pointsNumber) {
|
|
304
|
-
this.pointClusters = undefined
|
|
305
|
-
} else {
|
|
306
|
-
this.pointClusters = this.inputPointClusters
|
|
307
|
-
}
|
|
308
|
-
if (this.inputClusterPositions === undefined) {
|
|
309
|
-
this.clusterPositions = undefined
|
|
310
|
-
} else {
|
|
311
|
-
this.clusterPositions = this.inputClusterPositions
|
|
312
|
-
}
|
|
313
|
-
if (this.inputClusterStrength === undefined || this.inputClusterStrength.length !== this.pointsNumber) {
|
|
314
|
-
this.clusterStrength = undefined
|
|
315
|
-
} else {
|
|
316
|
-
this.clusterStrength = this.inputClusterStrength
|
|
317
|
-
}
|
|
318
|
-
}
|
|
319
|
-
|
|
320
|
-
public update (): void {
|
|
321
|
-
this.updatePoints()
|
|
322
|
-
this.updatePointColor()
|
|
323
|
-
this.updatePointSize()
|
|
324
|
-
this.updatePointShape()
|
|
325
|
-
this.updatePointImageIndices()
|
|
326
|
-
this.updatePointImageSizes()
|
|
327
|
-
|
|
328
|
-
this.updateLinks()
|
|
329
|
-
this.updateLinkColor()
|
|
330
|
-
this.updateLinkWidth()
|
|
331
|
-
this.updateArrows()
|
|
332
|
-
this.updateLinkStrength()
|
|
333
|
-
|
|
334
|
-
this.updateClusters()
|
|
335
|
-
|
|
336
|
-
this._createAdjacencyLists()
|
|
337
|
-
this._calculateDegrees()
|
|
338
|
-
}
|
|
339
|
-
|
|
340
|
-
public getAdjacentIndices (index: number): number[] | undefined {
|
|
341
|
-
return [...(this.sourceIndexToTargetIndices?.[index]?.map(d => d[0]) || []), ...(this.targetIndexToSourceIndices?.[index]?.map(d => d[0]) || [])]
|
|
342
|
-
}
|
|
343
|
-
|
|
344
|
-
private _createAdjacencyLists (): void {
|
|
345
|
-
if (this.linksNumber === undefined || this.links === undefined) {
|
|
346
|
-
this.sourceIndexToTargetIndices = undefined
|
|
347
|
-
this.targetIndexToSourceIndices = undefined
|
|
348
|
-
return
|
|
349
|
-
}
|
|
350
|
-
|
|
351
|
-
this.sourceIndexToTargetIndices = new Array(this.pointsNumber).fill(undefined)
|
|
352
|
-
this.targetIndexToSourceIndices = new Array(this.pointsNumber).fill(undefined)
|
|
353
|
-
for (let i = 0; i < this.linksNumber; i++) {
|
|
354
|
-
const sourceIndex = this.links[i * 2]
|
|
355
|
-
const targetIndex = this.links[i * 2 + 1]
|
|
356
|
-
if (sourceIndex !== undefined && targetIndex !== undefined) {
|
|
357
|
-
if (this.sourceIndexToTargetIndices[sourceIndex] === undefined) this.sourceIndexToTargetIndices[sourceIndex] = []
|
|
358
|
-
this.sourceIndexToTargetIndices[sourceIndex]?.push([targetIndex, i])
|
|
359
|
-
|
|
360
|
-
if (this.targetIndexToSourceIndices[targetIndex] === undefined) this.targetIndexToSourceIndices[targetIndex] = []
|
|
361
|
-
this.targetIndexToSourceIndices[targetIndex]?.push([sourceIndex, i])
|
|
362
|
-
}
|
|
363
|
-
}
|
|
364
|
-
}
|
|
365
|
-
|
|
366
|
-
private _calculateDegrees (): void {
|
|
367
|
-
if (this.pointsNumber === undefined) {
|
|
368
|
-
this.degree = undefined
|
|
369
|
-
this.inDegree = undefined
|
|
370
|
-
this.outDegree = undefined
|
|
371
|
-
return
|
|
372
|
-
}
|
|
373
|
-
|
|
374
|
-
this.degree = new Array(this.pointsNumber).fill(0)
|
|
375
|
-
this.inDegree = new Array(this.pointsNumber).fill(0)
|
|
376
|
-
this.outDegree = new Array(this.pointsNumber).fill(0)
|
|
377
|
-
|
|
378
|
-
for (let i = 0; i < this.pointsNumber; i++) {
|
|
379
|
-
this.inDegree[i] = this.targetIndexToSourceIndices?.[i]?.length ?? 0
|
|
380
|
-
this.outDegree[i] = this.sourceIndexToTargetIndices?.[i]?.length ?? 0
|
|
381
|
-
this.degree[i] = (this.inDegree[i] ?? 0) + (this.outDegree[i] ?? 0)
|
|
382
|
-
}
|
|
383
|
-
}
|
|
384
|
-
}
|
|
@@ -1,46 +0,0 @@
|
|
|
1
|
-
precision highp float;
|
|
2
|
-
|
|
3
|
-
varying vec4 rgbaColor;
|
|
4
|
-
varying vec2 pos;
|
|
5
|
-
varying float arrowLength;
|
|
6
|
-
varying float useArrow;
|
|
7
|
-
varying float smoothing;
|
|
8
|
-
varying float arrowWidthFactor;
|
|
9
|
-
varying float linkIndex;
|
|
10
|
-
|
|
11
|
-
// renderMode: 0.0 = normal rendering, 1.0 = index buffer rendering for picking
|
|
12
|
-
uniform float renderMode;
|
|
13
|
-
|
|
14
|
-
float map(float value, float min1, float max1, float min2, float max2) {
|
|
15
|
-
return min2 + (value - min1) * (max2 - min2) / (max1 - min1);
|
|
16
|
-
}
|
|
17
|
-
|
|
18
|
-
void main() {
|
|
19
|
-
float opacity = 1.0;
|
|
20
|
-
vec3 color = rgbaColor.rgb;
|
|
21
|
-
|
|
22
|
-
if (useArrow > 0.5) {
|
|
23
|
-
float end_arrow = 0.5 + arrowLength / 2.0;
|
|
24
|
-
float start_arrow = end_arrow - arrowLength;
|
|
25
|
-
float arrowWidthDelta = arrowWidthFactor / 2.0;
|
|
26
|
-
float linkOpacity = rgbaColor.a * smoothstep(0.5 - arrowWidthDelta, 0.5 - arrowWidthDelta - smoothing / 2.0, abs(pos.y));
|
|
27
|
-
float arrowOpacity = 1.0;
|
|
28
|
-
if (pos.x > start_arrow && pos.x < start_arrow + arrowLength) {
|
|
29
|
-
float xmapped = map(pos.x, start_arrow, end_arrow, 0.0, 1.0);
|
|
30
|
-
arrowOpacity = rgbaColor.a * smoothstep(xmapped - smoothing, xmapped, map(abs(pos.y), 0.5, 0.0, 0.0, 1.0));
|
|
31
|
-
if (linkOpacity != arrowOpacity) {
|
|
32
|
-
linkOpacity = max(linkOpacity, arrowOpacity);
|
|
33
|
-
}
|
|
34
|
-
}
|
|
35
|
-
opacity = linkOpacity;
|
|
36
|
-
} else opacity = rgbaColor.a * smoothstep(0.5, 0.5 - smoothing, abs(pos.y));
|
|
37
|
-
|
|
38
|
-
if (renderMode > 0.0) {
|
|
39
|
-
if (opacity > 0.0) {
|
|
40
|
-
gl_FragColor = vec4(linkIndex, 0.0, 0.0, 1.0);
|
|
41
|
-
} else {
|
|
42
|
-
gl_FragColor = vec4(-1.0, 0.0, 0.0, 0.0);
|
|
43
|
-
}
|
|
44
|
-
} else gl_FragColor = vec4(color, opacity);
|
|
45
|
-
|
|
46
|
-
}
|
|
@@ -1,194 +0,0 @@
|
|
|
1
|
-
precision highp float;
|
|
2
|
-
|
|
3
|
-
attribute vec2 position, pointA, pointB;
|
|
4
|
-
attribute vec4 color;
|
|
5
|
-
attribute float width;
|
|
6
|
-
attribute float arrow;
|
|
7
|
-
attribute float linkIndices;
|
|
8
|
-
|
|
9
|
-
uniform sampler2D positionsTexture;
|
|
10
|
-
uniform sampler2D pointGreyoutStatus;
|
|
11
|
-
uniform mat3 transformationMatrix;
|
|
12
|
-
uniform float pointsTextureSize;
|
|
13
|
-
uniform float widthScale;
|
|
14
|
-
uniform float linkArrowsSizeScale;
|
|
15
|
-
uniform float spaceSize;
|
|
16
|
-
uniform vec2 screenSize;
|
|
17
|
-
uniform vec2 linkVisibilityDistanceRange;
|
|
18
|
-
uniform float linkVisibilityMinTransparency;
|
|
19
|
-
uniform float linkOpacity;
|
|
20
|
-
uniform float greyoutOpacity;
|
|
21
|
-
uniform float curvedWeight;
|
|
22
|
-
uniform float curvedLinkControlPointDistance;
|
|
23
|
-
uniform float curvedLinkSegments;
|
|
24
|
-
uniform bool scaleLinksOnZoom;
|
|
25
|
-
uniform float maxPointSize;
|
|
26
|
-
// renderMode: 0.0 = normal rendering, 1.0 = index buffer rendering for picking
|
|
27
|
-
uniform float renderMode;
|
|
28
|
-
uniform float hoveredLinkIndex;
|
|
29
|
-
uniform vec4 hoveredLinkColor;
|
|
30
|
-
uniform float hoveredLinkWidthIncrease;
|
|
31
|
-
|
|
32
|
-
varying vec4 rgbaColor;
|
|
33
|
-
varying vec2 pos;
|
|
34
|
-
varying float arrowLength;
|
|
35
|
-
varying float useArrow;
|
|
36
|
-
varying float smoothing;
|
|
37
|
-
varying float arrowWidthFactor;
|
|
38
|
-
varying float linkIndex;
|
|
39
|
-
|
|
40
|
-
float map(float value, float min1, float max1, float min2, float max2) {
|
|
41
|
-
return min2 + (value - min1) * (max2 - min2) / (max1 - min1);
|
|
42
|
-
}
|
|
43
|
-
|
|
44
|
-
vec2 conicParametricCurve(vec2 A, vec2 B, vec2 ControlPoint, float t, float w) {
|
|
45
|
-
vec2 divident = (1.0 - t) * (1.0 - t) * A + 2.0 * (1.0 - t) * t * w * ControlPoint + t * t * B;
|
|
46
|
-
float divisor = (1.0 - t) * (1.0 - t) + 2.0 * (1.0 - t) * t * w + t * t;
|
|
47
|
-
return divident / divisor;
|
|
48
|
-
}
|
|
49
|
-
|
|
50
|
-
float calculateLinkWidth(float width) {
|
|
51
|
-
float linkWidth;
|
|
52
|
-
if (scaleLinksOnZoom) {
|
|
53
|
-
// Use original width if links should scale with zoom
|
|
54
|
-
linkWidth = width;
|
|
55
|
-
} else {
|
|
56
|
-
// Adjust width based on zoom level to maintain visual size
|
|
57
|
-
linkWidth = width / transformationMatrix[0][0];
|
|
58
|
-
// Apply a non-linear scaling to avoid extreme widths
|
|
59
|
-
linkWidth *= min(5.0, max(1.0, transformationMatrix[0][0] * 0.01));
|
|
60
|
-
}
|
|
61
|
-
// Limit link width based on whether it has an arrow
|
|
62
|
-
if (useArrow > 0.5) {
|
|
63
|
-
return min(linkWidth, (maxPointSize * 2.0) / transformationMatrix[0][0]);
|
|
64
|
-
} else {
|
|
65
|
-
return min(linkWidth, maxPointSize / transformationMatrix[0][0]);
|
|
66
|
-
}
|
|
67
|
-
}
|
|
68
|
-
|
|
69
|
-
float calculateArrowWidth(float arrowWidth) {
|
|
70
|
-
if (scaleLinksOnZoom) {
|
|
71
|
-
return arrowWidth;
|
|
72
|
-
} else {
|
|
73
|
-
// Apply the same scaling logic as calculateLinkWidth to maintain proportionality
|
|
74
|
-
arrowWidth = arrowWidth / transformationMatrix[0][0];
|
|
75
|
-
// Apply the same non-linear scaling to avoid extreme widths
|
|
76
|
-
arrowWidth *= min(5.0, max(1.0, transformationMatrix[0][0] * 0.01));
|
|
77
|
-
return arrowWidth;
|
|
78
|
-
}
|
|
79
|
-
}
|
|
80
|
-
|
|
81
|
-
void main() {
|
|
82
|
-
pos = position;
|
|
83
|
-
linkIndex = linkIndices;
|
|
84
|
-
|
|
85
|
-
vec2 pointTexturePosA = (pointA + 0.5) / pointsTextureSize;
|
|
86
|
-
vec2 pointTexturePosB = (pointB + 0.5) / pointsTextureSize;
|
|
87
|
-
|
|
88
|
-
vec4 greyoutStatusA = texture2D(pointGreyoutStatus, pointTexturePosA);
|
|
89
|
-
vec4 greyoutStatusB = texture2D(pointGreyoutStatus, pointTexturePosB);
|
|
90
|
-
|
|
91
|
-
vec4 pointPositionA = texture2D(positionsTexture, pointTexturePosA);
|
|
92
|
-
vec4 pointPositionB = texture2D(positionsTexture, pointTexturePosB);
|
|
93
|
-
vec2 a = pointPositionA.xy;
|
|
94
|
-
vec2 b = pointPositionB.xy;
|
|
95
|
-
|
|
96
|
-
// Calculate direction vector and its perpendicular
|
|
97
|
-
vec2 xBasis = b - a;
|
|
98
|
-
vec2 yBasis = normalize(vec2(-xBasis.y, xBasis.x));
|
|
99
|
-
|
|
100
|
-
// Calculate link distance and control point for curved link
|
|
101
|
-
float linkDist = length(xBasis);
|
|
102
|
-
float h = curvedLinkControlPointDistance;
|
|
103
|
-
vec2 controlPoint = (a + b) / 2.0 + yBasis * linkDist * h;
|
|
104
|
-
|
|
105
|
-
// Convert link distance to screen pixels
|
|
106
|
-
float linkDistPx = linkDist * transformationMatrix[0][0];
|
|
107
|
-
|
|
108
|
-
// Calculate line width using the width scale
|
|
109
|
-
float linkWidth = width * widthScale;
|
|
110
|
-
float k = 2.0;
|
|
111
|
-
// Arrow width is proportionally larger than the line width
|
|
112
|
-
float arrowWidth = linkWidth * k;
|
|
113
|
-
arrowWidth *= linkArrowsSizeScale;
|
|
114
|
-
|
|
115
|
-
// Ensure arrow width difference is non-negative to prevent unwanted changes to link width
|
|
116
|
-
float arrowWidthDifference = max(0.0, arrowWidth - linkWidth);
|
|
117
|
-
|
|
118
|
-
// Calculate arrow width in pixels
|
|
119
|
-
float arrowWidthPx = calculateArrowWidth(arrowWidth);
|
|
120
|
-
|
|
121
|
-
// Calculate arrow length proportional to its width
|
|
122
|
-
// 0.866 is approximately sqrt(3)/2 - related to equilateral triangle geometry
|
|
123
|
-
// Cap the length to avoid overly long arrows on short links
|
|
124
|
-
arrowLength = min(0.3, (0.866 * arrowWidthPx * 2.0) / linkDist);
|
|
125
|
-
|
|
126
|
-
useArrow = arrow;
|
|
127
|
-
if (useArrow > 0.5) {
|
|
128
|
-
linkWidth += arrowWidthDifference;
|
|
129
|
-
}
|
|
130
|
-
|
|
131
|
-
arrowWidthFactor = arrowWidthDifference / linkWidth;
|
|
132
|
-
|
|
133
|
-
// Calculate final link width in pixels with smoothing
|
|
134
|
-
float linkWidthPx = calculateLinkWidth(linkWidth);
|
|
135
|
-
|
|
136
|
-
if (renderMode > 0.0) {
|
|
137
|
-
// Add 5 pixels padding for better hover detection
|
|
138
|
-
linkWidthPx += 5.0 / transformationMatrix[0][0];
|
|
139
|
-
} else {
|
|
140
|
-
// Add pixel increase if this is the hovered link
|
|
141
|
-
if (hoveredLinkIndex == linkIndex) {
|
|
142
|
-
linkWidthPx += hoveredLinkWidthIncrease / transformationMatrix[0][0];
|
|
143
|
-
}
|
|
144
|
-
}
|
|
145
|
-
float smoothingPx = 0.5 / transformationMatrix[0][0];
|
|
146
|
-
smoothing = smoothingPx / linkWidthPx;
|
|
147
|
-
linkWidthPx += smoothingPx;
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
// Calculate final color with opacity based on link distance
|
|
152
|
-
vec3 rgbColor = color.rgb;
|
|
153
|
-
// Adjust opacity based on link distance
|
|
154
|
-
float opacity = color.a * linkOpacity * max(linkVisibilityMinTransparency, map(linkDistPx, linkVisibilityDistanceRange.g, linkVisibilityDistanceRange.r, 0.0, 1.0));
|
|
155
|
-
|
|
156
|
-
// Apply greyed out opacity if either endpoint is greyed out
|
|
157
|
-
if (greyoutStatusA.r > 0.0 || greyoutStatusB.r > 0.0) {
|
|
158
|
-
opacity *= greyoutOpacity;
|
|
159
|
-
}
|
|
160
|
-
|
|
161
|
-
// Pass final color to fragment shader
|
|
162
|
-
rgbaColor = vec4(rgbColor, opacity);
|
|
163
|
-
|
|
164
|
-
// Apply hover color if this is the hovered link and hover color is defined
|
|
165
|
-
if (hoveredLinkIndex == linkIndex && hoveredLinkColor.a > -0.5) {
|
|
166
|
-
// Keep existing RGB values but multiply opacity with hover color opacity
|
|
167
|
-
rgbaColor.rgb = hoveredLinkColor.rgb;
|
|
168
|
-
rgbaColor.a *= hoveredLinkColor.a;
|
|
169
|
-
}
|
|
170
|
-
|
|
171
|
-
// Calculate position on the curved path
|
|
172
|
-
float t = position.x;
|
|
173
|
-
float w = curvedWeight;
|
|
174
|
-
|
|
175
|
-
float tPrev = t - 1.0 / curvedLinkSegments;
|
|
176
|
-
float tNext = t + 1.0 / curvedLinkSegments;
|
|
177
|
-
|
|
178
|
-
vec2 pointCurr = conicParametricCurve(a, b, controlPoint, t, w);
|
|
179
|
-
|
|
180
|
-
vec2 pointPrev = conicParametricCurve(a, b, controlPoint, max(0.0, tPrev), w);
|
|
181
|
-
vec2 pointNext = conicParametricCurve(a, b, controlPoint, min(tNext, 1.0), w);
|
|
182
|
-
|
|
183
|
-
vec2 xBasisCurved = pointNext - pointPrev;
|
|
184
|
-
vec2 yBasisCurved = normalize(vec2(-xBasisCurved.y, xBasisCurved.x));
|
|
185
|
-
|
|
186
|
-
pointCurr += yBasisCurved * linkWidthPx * position.y;
|
|
187
|
-
|
|
188
|
-
// Transform to clip space coordinates
|
|
189
|
-
vec2 p = 2.0 * pointCurr / spaceSize - 1.0;
|
|
190
|
-
p *= spaceSize / screenSize;
|
|
191
|
-
vec3 final = transformationMatrix * vec3(p, 1);
|
|
192
|
-
|
|
193
|
-
gl_Position = vec4(final.rg, 0, 1);
|
|
194
|
-
}
|
|
@@ -1,18 +0,0 @@
|
|
|
1
|
-
import { scalePow } from 'd3-scale'
|
|
2
|
-
import { range } from 'd3-array'
|
|
3
|
-
|
|
4
|
-
export const getCurveLineGeometry = (segments: number): number[][] => {
|
|
5
|
-
const scale = scalePow()
|
|
6
|
-
.exponent(2)
|
|
7
|
-
.range([0, 1])
|
|
8
|
-
.domain([-1, 1])
|
|
9
|
-
|
|
10
|
-
const hodographValues = range(0, segments).map(d => -0.5 + d / segments)
|
|
11
|
-
hodographValues.push(0.5)
|
|
12
|
-
const result = new Array(hodographValues.length * 2)
|
|
13
|
-
hodographValues.forEach((d, i) => {
|
|
14
|
-
result[i * 2] = [scale(d * 2), 0.5]
|
|
15
|
-
result[i * 2 + 1] = [scale(d * 2), -0.5]
|
|
16
|
-
})
|
|
17
|
-
return result
|
|
18
|
-
}
|
|
@@ -1,27 +0,0 @@
|
|
|
1
|
-
precision highp float;
|
|
2
|
-
|
|
3
|
-
uniform sampler2D linkIndexTexture;
|
|
4
|
-
uniform vec2 mousePosition;
|
|
5
|
-
uniform vec2 screenSize;
|
|
6
|
-
|
|
7
|
-
varying vec2 vTexCoord;
|
|
8
|
-
|
|
9
|
-
void main() {
|
|
10
|
-
// Convert mouse position to texture coordinates
|
|
11
|
-
vec2 texCoord = mousePosition / screenSize;
|
|
12
|
-
|
|
13
|
-
// Read the link index from the linkIndexFbo texture at mouse position
|
|
14
|
-
vec4 linkIndexData = texture2D(linkIndexTexture, texCoord);
|
|
15
|
-
|
|
16
|
-
// Extract the link index (stored in the red channel)
|
|
17
|
-
float linkIndex = linkIndexData.r;
|
|
18
|
-
|
|
19
|
-
// Check if there's a valid link at this position (alpha > 0)
|
|
20
|
-
if (linkIndexData.a > 0.0 && linkIndex >= 0.0) {
|
|
21
|
-
// Output the link index
|
|
22
|
-
gl_FragColor = vec4(linkIndex, 0.0, 0.0, 1.0);
|
|
23
|
-
} else {
|
|
24
|
-
// No link at this position, output -1 to indicate no hover
|
|
25
|
-
gl_FragColor = vec4(-1.0, 0.0, 0.0, 0.0);
|
|
26
|
-
}
|
|
27
|
-
}
|