Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
godotengine
GitHub Repository: godotengine/godot
Path: blob/master/thirdparty/embree/kernels/common/scene_points.h
9905 views
1
// Copyright 2009-2021 Intel Corporation
2
// SPDX-License-Identifier: Apache-2.0
3
4
#pragma once
5
6
#include "buffer.h"
7
#include "default.h"
8
#include "geometry.h"
9
10
namespace embree
11
{
12
/*! represents an array of points */
13
struct Points : public Geometry
14
{
15
/*! type of this geometry */
16
static const Geometry::GTypeMask geom_type = Geometry::MTY_POINTS;
17
18
public:
19
/*! line segments construction */
20
Points(Device* device, Geometry::GType gtype);
21
22
public:
23
void setMask(unsigned mask);
24
void setNumTimeSteps(unsigned int numTimeSteps);
25
void setVertexAttributeCount(unsigned int N);
26
void setBuffer(RTCBufferType type,
27
unsigned int slot,
28
RTCFormat format,
29
const Ref<Buffer>& buffer,
30
size_t offset,
31
size_t stride,
32
unsigned int num);
33
void* getBufferData(RTCBufferType type, unsigned int slot, BufferDataPointerType pointerType);
34
void updateBuffer(RTCBufferType type, unsigned int slot);
35
void commit();
36
bool verify();
37
void setMaxRadiusScale(float s);
38
void addElementsToCount (GeometryCounts & counts) const;
39
size_t getGeometryDataDeviceByteSize() const;
40
void convertToDeviceRepresentation(size_t offset, char* data_host, char* data_device) const;
41
42
public:
43
/*! returns the number of vertices */
44
__forceinline size_t numVertices() const {
45
return vertices[0].size();
46
}
47
48
/*! returns i'th vertex of the first time step */
49
__forceinline Vec3ff vertex(size_t i) const {
50
return vertices0[i];
51
}
52
53
/*! returns i'th vertex of the first time step */
54
__forceinline const char* vertexPtr(size_t i) const {
55
return vertices0.getPtr(i);
56
}
57
58
/*! returns i'th normal of the first time step */
59
__forceinline Vec3fa normal(size_t i) const {
60
return normals0[i];
61
}
62
63
/*! returns i'th radius of the first time step */
64
__forceinline float radius(size_t i) const {
65
return vertices0[i].w;
66
}
67
68
/*! returns i'th vertex of itime'th timestep */
69
__forceinline Vec3ff vertex(size_t i, size_t itime) const {
70
return vertices[itime][i];
71
}
72
73
/*! returns i'th vertex of for specified time */
74
__forceinline Vec3ff vertex(size_t i, float time) const
75
{
76
float ftime;
77
const size_t itime = timeSegment(time, ftime);
78
const float t0 = 1.0f - ftime;
79
const float t1 = ftime;
80
Vec3ff v0 = vertex(i, itime+0);
81
Vec3ff v1 = vertex(i, itime+1);
82
return madd(Vec3ff(t0),v0,t1*v1);
83
}
84
85
/*! returns i'th vertex of for specified time */
86
__forceinline Vec3ff vertex_safe(size_t i, float time) const
87
{
88
if (hasMotionBlur()) return vertex(i,time);
89
else return vertex(i);
90
}
91
92
/*! returns i'th vertex of itime'th timestep */
93
__forceinline const char* vertexPtr(size_t i, size_t itime) const {
94
return vertices[itime].getPtr(i);
95
}
96
97
/*! returns i'th normal of itime'th timestep */
98
__forceinline Vec3fa normal(size_t i, size_t itime) const {
99
return normals[itime][i];
100
}
101
102
/*! returns i'th normal of for specified time */
103
__forceinline Vec3fa normal(size_t i, float time) const
104
{
105
float ftime;
106
const size_t itime = timeSegment(time, ftime);
107
const float t0 = 1.0f - ftime;
108
const float t1 = ftime;
109
Vec3fa n0 = normal(i, itime+0);
110
Vec3fa n1 = normal(i, itime+1);
111
return madd(Vec3fa(t0),n0,t1*n1);
112
}
113
114
/*! returns i'th normal of for specified time */
115
__forceinline Vec3fa normal_safe(size_t i, float time) const
116
{
117
if (hasMotionBlur()) return normal(i,time);
118
else return normal(i);
119
}
120
121
/*! returns i'th radius of itime'th timestep */
122
__forceinline float radius(size_t i, size_t itime) const {
123
return vertices[itime][i].w;
124
}
125
126
/*! returns i'th radius of for specified time */
127
__forceinline float radius(size_t i, float time) const
128
{
129
float ftime;
130
const size_t itime = timeSegment(time, ftime);
131
const float t0 = 1.0f - ftime;
132
const float t1 = ftime;
133
float r0 = radius(i, itime+0);
134
float r1 = radius(i, itime+1);
135
return madd(t0,r0,t1*r1);
136
}
137
138
/*! returns i'th radius of for specified time */
139
__forceinline float radius_safe(size_t i, float time) const
140
{
141
if (hasMotionBlur()) return radius(i,time);
142
else return radius(i);
143
}
144
145
/*! calculates bounding box of i'th line segment */
146
__forceinline BBox3fa bounds(const Vec3ff& v0) const {
147
return enlarge(BBox3fa(v0), maxRadiusScale*Vec3fa(v0.w));
148
}
149
150
/*! calculates bounding box of i'th line segment */
151
__forceinline BBox3fa bounds(size_t i) const
152
{
153
const Vec3ff v0 = vertex(i);
154
return bounds(v0);
155
}
156
157
/*! calculates bounding box of i'th line segment for the itime'th time step */
158
__forceinline BBox3fa bounds(size_t i, size_t itime) const
159
{
160
const Vec3ff v0 = vertex(i, itime);
161
return bounds(v0);
162
}
163
164
/*! calculates bounding box of i'th line segment */
165
__forceinline BBox3fa bounds(const LinearSpace3fa& space, size_t i) const
166
{
167
const Vec3ff v0 = vertex(i);
168
const Vec3ff w0(xfmVector(space, (Vec3fa)v0), v0.w);
169
return bounds(w0);
170
}
171
172
/*! calculates bounding box of i'th line segment for the itime'th time step */
173
__forceinline BBox3fa bounds(const LinearSpace3fa& space, size_t i, size_t itime) const
174
{
175
const Vec3ff v0 = vertex(i, itime);
176
const Vec3ff w0(xfmVector(space, (Vec3fa)v0), v0.w);
177
return bounds(w0);
178
}
179
180
/*! check if the i'th primitive is valid at the itime'th timestep */
181
__forceinline bool valid(size_t i, size_t itime) const {
182
return valid(i, make_range(itime, itime));
183
}
184
185
/*! check if the i'th primitive is valid between the specified time range */
186
__forceinline bool valid(size_t i, const range<size_t>& itime_range) const
187
{
188
const unsigned int index = (unsigned int)i;
189
if (index >= numVertices())
190
return false;
191
192
for (size_t itime = itime_range.begin(); itime <= itime_range.end(); itime++) {
193
const Vec3ff v0 = vertex(index + 0, itime);
194
if (unlikely(!isvalid4(v0)))
195
return false;
196
if (v0.w < 0.0f)
197
return false;
198
}
199
return true;
200
}
201
202
/*! calculates the linear bounds of the i'th primitive at the itimeGlobal'th time segment */
203
__forceinline LBBox3fa linearBounds(size_t i, size_t itime) const {
204
return LBBox3fa(bounds(i, itime + 0), bounds(i, itime + 1));
205
}
206
207
/*! calculates the build bounds of the i'th primitive, if it's valid */
208
__forceinline bool buildBounds(size_t i, BBox3fa* bbox) const
209
{
210
if (!valid(i, 0))
211
return false;
212
*bbox = bounds(i);
213
return true;
214
}
215
216
/*! calculates the build bounds of the i'th primitive at the itime'th time segment, if it's valid */
217
__forceinline bool buildBounds(size_t i, size_t itime, BBox3fa& bbox) const
218
{
219
if (!valid(i, itime + 0) || !valid(i, itime + 1))
220
return false;
221
bbox = bounds(i, itime); // use bounds of first time step in builder
222
return true;
223
}
224
225
/*! calculates the linear bounds of the i'th primitive for the specified time range */
226
__forceinline LBBox3fa linearBounds(size_t primID, const BBox1f& dt) const {
227
return LBBox3fa([&](size_t itime) { return bounds(primID, itime); }, dt, time_range, fnumTimeSegments);
228
}
229
230
/*! calculates the linear bounds of the i'th primitive for the specified time range */
231
__forceinline LBBox3fa linearBounds(const LinearSpace3fa& space, size_t primID, const BBox1f& dt) const {
232
return LBBox3fa([&](size_t itime) { return bounds(space, primID, itime); }, dt, time_range, fnumTimeSegments);
233
}
234
235
/*! calculates the linear bounds of the i'th primitive for the specified time range */
236
__forceinline bool linearBounds(size_t i, const BBox1f& time_range, LBBox3fa& bbox) const
237
{
238
if (!valid(i, timeSegmentRange(time_range))) return false;
239
bbox = linearBounds(i, time_range);
240
return true;
241
}
242
243
/*! get fast access to first vertex buffer */
244
__forceinline float * getCompactVertexArray () const {
245
return (float*) vertices0.getPtr();
246
}
247
248
__forceinline float projectedPrimitiveArea(const size_t i) const {
249
const float R = radius(i);
250
return 1 + 2*M_PI*R*R;
251
}
252
253
public:
254
BufferView<Vec3ff> vertices0; //!< fast access to first vertex buffer
255
BufferView<Vec3fa> normals0; //!< fast access to first normal buffer
256
Device::vector<BufferView<Vec3ff>> vertices = device; //!< vertex array for each timestep
257
Device::vector<BufferView<Vec3fa>> normals = device; //!< normal array for each timestep
258
Device::vector<BufferView<char>> vertexAttribs = device; //!< user buffers
259
float maxRadiusScale = 1.0; //!< maximal min-width scaling of curve radii
260
};
261
262
namespace isa
263
{
264
struct PointsISA : public Points
265
{
266
PointsISA(Device* device, Geometry::GType gtype) : Points(device, gtype) {}
267
268
Vec3fa computeDirection(unsigned int primID) const
269
{
270
return Vec3fa(1, 0, 0);
271
}
272
273
Vec3fa computeDirection(unsigned int primID, size_t time) const
274
{
275
return Vec3fa(1, 0, 0);
276
}
277
278
PrimInfo createPrimRefArray(PrimRef* prims, const range<size_t>& r, size_t k, unsigned int geomID) const
279
{
280
PrimInfo pinfo(empty);
281
for (size_t j = r.begin(); j < r.end(); j++) {
282
BBox3fa bounds = empty;
283
if (!buildBounds(j, &bounds))
284
continue;
285
const PrimRef prim(bounds, geomID, unsigned(j));
286
pinfo.add_center2(prim);
287
prims[k++] = prim;
288
}
289
return pinfo;
290
}
291
292
PrimInfo createPrimRefArrayMB(mvector<PrimRef>& prims, size_t itime, const range<size_t>& r, size_t k, unsigned int geomID) const
293
{
294
PrimInfo pinfo(empty);
295
for (size_t j = r.begin(); j < r.end(); j++) {
296
BBox3fa bounds = empty;
297
if (!buildBounds(j, itime, bounds))
298
continue;
299
const PrimRef prim(bounds, geomID, unsigned(j));
300
pinfo.add_center2(prim);
301
prims[k++] = prim;
302
}
303
return pinfo;
304
}
305
306
PrimInfo createPrimRefArrayMB(PrimRef* prims, const BBox1f& time_range, const range<size_t>& r, size_t k, unsigned int geomID) const
307
{
308
PrimInfo pinfo(empty);
309
const BBox1f t0t1 = BBox1f::intersect(getTimeRange(), time_range);
310
if (t0t1.empty()) return pinfo;
311
312
for (size_t j = r.begin(); j < r.end(); j++) {
313
LBBox3fa lbounds = empty;
314
if (!linearBounds(j, t0t1, lbounds))
315
continue;
316
const PrimRef prim(lbounds.bounds(), geomID, unsigned(j));
317
pinfo.add_center2(prim);
318
prims[k++] = prim;
319
}
320
return pinfo;
321
}
322
323
PrimInfoMB createPrimRefMBArray(mvector<PrimRefMB>& prims,
324
const BBox1f& t0t1,
325
const range<size_t>& r,
326
size_t k,
327
unsigned int geomID) const
328
{
329
PrimInfoMB pinfo(empty);
330
for (size_t j = r.begin(); j < r.end(); j++) {
331
if (!valid(j, timeSegmentRange(t0t1)))
332
continue;
333
const PrimRefMB prim(linearBounds(j, t0t1), this->numTimeSegments(), this->time_range, this->numTimeSegments(), geomID, unsigned(j));
334
pinfo.add_primref(prim);
335
prims[k++] = prim;
336
}
337
return pinfo;
338
}
339
340
BBox3fa vbounds(size_t i) const
341
{
342
return bounds(i);
343
}
344
345
BBox3fa vbounds(const LinearSpace3fa& space, size_t i) const
346
{
347
return bounds(space, i);
348
}
349
350
LBBox3fa vlinearBounds(size_t primID, const BBox1f& time_range) const
351
{
352
return linearBounds(primID, time_range);
353
}
354
355
LBBox3fa vlinearBounds(const LinearSpace3fa& space, size_t primID, const BBox1f& time_range) const
356
{
357
return linearBounds(space, primID, time_range);
358
}
359
};
360
} // namespace isa
361
362
DECLARE_ISA_FUNCTION(Points*, createPoints, Device* COMMA Geometry::GType);
363
} // namespace embree
364
365