Blender V4.3
overlay_next_shape.cc
Go to the documentation of this file.
1/* SPDX-FileCopyrightText: 2023 Blender Authors
2 *
3 * SPDX-License-Identifier: GPL-2.0-or-later */
4
10
11namespace blender::draw::overlay {
12
13/* Matches Vertex Format. */
14struct Vertex {
16 int vclass;
17};
18
24
25/* TODO(fclem): Might be good to remove for simplicity. */
31
32/* Caller gets ownership of the #gpu::VertBuf. */
34{
35 static GPUVertFormat format = {0};
36 if (format.attr_len == 0) {
39 }
40
42 GPU_vertbuf_data_alloc(*vbo, vector.size());
43 vbo->data<Vertex>().copy_from(vector);
44 return vbo;
45}
46
61
76
99
100static constexpr int diamond_nsegments = 4;
101static constexpr int inner_nsegments = 8;
102static constexpr int outer_nsegments = 10;
103static constexpr int circle_nsegments = 32;
104
105static constexpr float bone_box_verts[8][3] = {
106 {1.0f, 0.0f, 1.0f},
107 {1.0f, 0.0f, -1.0f},
108 {-1.0f, 0.0f, -1.0f},
109 {-1.0f, 0.0f, 1.0f},
110 {1.0f, 1.0f, 1.0f},
111 {1.0f, 1.0f, -1.0f},
112 {-1.0f, 1.0f, -1.0f},
113 {-1.0f, 1.0f, 1.0f},
114};
115
116static constexpr std::array<uint, 24> bone_box_wire_lines = {
117 0, 1, 1, 2, 2, 3, 3, 0, 4, 5, 5, 6, 6, 7, 7, 4, 0, 4, 1, 5, 2, 6, 3, 7,
118};
119
120static const std::array<uint3, 12> bone_box_solid_tris{
121 uint3{0, 2, 1}, /* bottom */
122 {0, 3, 2},
123
124 {0, 1, 5}, /* sides */
125 {0, 5, 4},
126
127 {1, 2, 6},
128 {1, 6, 5},
129
130 {2, 3, 7},
131 {2, 7, 6},
132
133 {3, 0, 4},
134 {3, 4, 7},
135
136 {4, 5, 6}, /* top */
137 {4, 6, 7},
138};
139
144static const std::array<uint4, 12> bone_box_wire_lines_adjacency = {
145 uint4{4, 2, 0, 11},
146 {0, 1, 2, 8},
147 {2, 4, 1, 14},
148 {1, 0, 4, 20}, /* bottom */
149 {0, 8, 11, 14},
150 {2, 14, 8, 20},
151 {1, 20, 14, 11},
152 {4, 11, 20, 8}, /* top */
153 {20, 0, 11, 2},
154 {11, 2, 8, 1},
155 {8, 1, 14, 4},
156 {14, 4, 20, 0}, /* sides */
157};
158
159/* aligned with bone_box_solid_tris */
160static const std::array<float3, 12> bone_box_solid_normals = {
161 float3{0.0f, -1.0f, 0.0f},
162 {0.0f, -1.0f, 0.0f},
163
164 {1.0f, 0.0f, 0.0f},
165 {1.0f, 0.0f, 0.0f},
166
167 {0.0f, 0.0f, -1.0f},
168 {0.0f, 0.0f, -1.0f},
169
170 {-1.0f, 0.0f, 0.0f},
171 {-1.0f, 0.0f, 0.0f},
172
173 {0.0f, 0.0f, 1.0f},
174 {0.0f, 0.0f, 1.0f},
175
176 {0.0f, 1.0f, 0.0f},
177 {0.0f, 1.0f, 0.0f},
178};
179
180static const std::array<float3, 6> bone_octahedral_verts{
181 float3{0.0f, 0.0f, 0.0f},
182 {0.1f, 0.1f, 0.1f},
183 {0.1f, 0.1f, -0.1f},
184 {-0.1f, 0.1f, -0.1f},
185 {-0.1f, 0.1f, 0.1f},
186 {0.0f, 1.0f, 0.0f},
187};
188
195static const std::array<float3, 6> bone_octahedral_smooth_normals{
196 float3{0.0f, -1.0f, 0.0f},
197 {float(M_SQRT1_2), 0.0f, float(M_SQRT1_2)},
198 {float(M_SQRT1_2), 0.0f, -float(M_SQRT1_2)},
199 {-float(M_SQRT1_2), 0.0f, -float(M_SQRT1_2)},
200 {-float(M_SQRT1_2), 0.0f, float(M_SQRT1_2)},
201 {0.0f, 1.0f, 0.0f},
202};
203
204static const std::array<uint2, 12> bone_octahedral_wire_lines = {
205 uint2{0, 1},
206 {1, 5},
207 {5, 3},
208 {3, 0},
209 {0, 4},
210 {4, 5},
211 {5, 2},
212 {2, 0},
213 {1, 2},
214 {2, 3},
215 {3, 4},
216 {4, 1},
217};
218
219static const std::array<uint3, 8> bone_octahedral_solid_tris = {
220 uint3{2, 1, 0}, /* bottom */
221 {3, 2, 0},
222 {4, 3, 0},
223 {1, 4, 0},
224
225 {5, 1, 2}, /* top */
226 {5, 2, 3},
227 {5, 3, 4},
228 {5, 4, 1},
229};
230
242static const std::array<uint4, 12> bone_octahedral_wire_lines_adjacency = {
243 uint4{0, 1, 2, 6},
244 {0, 12, 1, 6},
245 {0, 3, 12, 6},
246 {0, 2, 3, 6},
247 {1, 6, 2, 3},
248 {1, 12, 6, 3},
249 {1, 0, 12, 3},
250 {1, 2, 0, 3},
251 {2, 0, 1, 12},
252 {2, 3, 0, 12},
253 {2, 6, 3, 12},
254 {2, 1, 6, 12},
255};
256
257/* aligned with bone_octahedral_solid_tris */
258static const float bone_octahedral_solid_normals[8][3] = {
259 {M_SQRT1_2, -M_SQRT1_2, 0.00000000f},
260 {-0.00000000f, -M_SQRT1_2, -M_SQRT1_2},
261 {-M_SQRT1_2, -M_SQRT1_2, 0.00000000f},
262 {0.00000000f, -M_SQRT1_2, M_SQRT1_2},
263 {0.99388373f, 0.11043154f, -0.00000000f},
264 {0.00000000f, 0.11043154f, -0.99388373f},
265 {-0.99388373f, 0.11043154f, 0.00000000f},
266 {0.00000000f, 0.11043154f, 0.99388373f},
267};
268
270 Vector<Vertex> &dest, Span<float2> verts, float z, int flag, bool dashed = false)
271{
272 const int step = dashed ? 2 : 1;
273 for (const int i : IndexRange(verts.size() / step)) {
274 for (const int j : IndexRange(2)) {
275 const float2 &cv = verts[(i * step + j) % verts.size()];
276 dest.append({{cv[0], cv[1], z}, flag});
277 }
278 }
279}
280
281static float light_distance_z_get(char axis, const bool start)
282{
283 switch (axis) {
284 case 'x': /* - X */
285 return start ? 0.4f : 0.3f;
286 case 'X': /* + X */
287 return start ? 0.6f : 0.7f;
288 case 'y': /* - Y */
289 return start ? 1.4f : 1.3f;
290 case 'Y': /* + Y */
291 return start ? 1.6f : 1.7f;
292 case 'z': /* - Z */
293 return start ? 2.4f : 2.3f;
294 case 'Z': /* + Z */
295 return start ? 2.6f : 2.7f;
296 }
297 return 0.0;
298}
299
300/* A single ring of vertices. */
301static Vector<float2> ring_vertices(const float radius,
302 const int segments,
303 const bool half = false)
304{
306 const float full = (half ? 1.0f : 2.0f) * math::numbers::pi;
307 for (const int angle_i : IndexRange(segments + (half ? 1 : 0))) {
308 const float angle = (full * angle_i) / segments;
309 verts.append(radius * float2(math::cos(angle), math::sin(angle)));
310 }
311 return verts;
312}
313
314/* Returns lines segment geometry forming 3 circles, one on each axis. */
315static Vector<Vertex> sphere_axes_circles(const float radius,
316 const VertexClass vclass,
317 const int segments)
318{
319 Vector<float2> ring = ring_vertices(radius, segments);
320
322 for (int axis : IndexRange(3)) {
323 for (int i : IndexRange(segments)) {
324 for (int j : IndexRange(2)) {
325 float2 cv = ring[(i + j) % segments];
326 if (axis == 0) {
327 verts.append({{cv[0], cv[1], 0.0f}, vclass});
328 }
329 else if (axis == 1) {
330 verts.append({{cv[0], 0.0f, cv[1]}, vclass});
331 }
332 else {
333 verts.append({{0.0f, cv[0], cv[1]}, vclass});
334 }
335 }
336 }
337 }
338 return verts;
339}
340
341static void light_append_direction_line(const char axis,
342 Span<float2> diamond,
344{
345 const float zsta = light_distance_z_get(axis, true);
346 const float zend = light_distance_z_get(axis, false);
347 verts.append({{0.0, 0.0, zsta}, VCLASS_LIGHT_DIST});
348 verts.append({{0.0, 0.0, zend}, VCLASS_LIGHT_DIST});
351}
352
358
359static VertShaded sphere_lat_lon_vert(const float2 &lat_pt, const float2 &lon_pt)
360{
361 const float x = lon_pt.y * lat_pt.x;
362 const float y = lon_pt.x;
363 const float z = lon_pt.y * lat_pt.y;
364 return VertShaded{{x, y, z}, VCLASS_EMPTY_SCALED, {x, y, z}};
365}
366
367static void append_sphere(Vector<VertShaded> &dest, const eDRWLevelOfDetail level_of_detail)
368{
369 /* Sphere shape resolution */
370 /* Low */
371 constexpr int drw_sphere_shape_latitude_low = 32;
372 constexpr int drw_sphere_shape_longitude_low = 24;
373 /* Medium */
374 constexpr int drw_sphere_shape_latitude_medium = 64;
375 constexpr int drw_sphere_shape_longitude_medium = 48;
376 /* High */
377 constexpr int drw_sphere_shape_latitude_high = 80;
378 constexpr int drw_sphere_shape_longitude_high = 60;
379
380 BLI_assert(level_of_detail >= DRW_LOD_LOW && level_of_detail < DRW_LOD_MAX);
381 const std::array<Vector<float2>, DRW_LOD_MAX> latitude_rings = {
382 ring_vertices(1.0f, drw_sphere_shape_latitude_low),
383 ring_vertices(1.0f, drw_sphere_shape_latitude_medium),
384 ring_vertices(1.0f, drw_sphere_shape_latitude_high)};
385 const std::array<Vector<float2>, DRW_LOD_MAX> longitude_half_rings = {
386 ring_vertices(1.0f, drw_sphere_shape_longitude_low, true),
387 ring_vertices(1.0f, drw_sphere_shape_longitude_medium, true),
388 ring_vertices(1.0f, drw_sphere_shape_longitude_high, true)};
389
390 const Vector<float2> &latitude_ring = latitude_rings[level_of_detail];
391 const Vector<float2> &longitude_half_ring = longitude_half_rings[level_of_detail];
392
393 for (const int i : latitude_ring.index_range()) {
394 const float2 lat_pt = latitude_ring[i];
395 const float2 next_lat_pt = latitude_ring[(i + 1) % latitude_ring.size()];
396 for (const int j : IndexRange(longitude_half_ring.size() - 1)) {
397 const float2 lon_pt = longitude_half_ring[j];
398 const float2 next_lon_pt = longitude_half_ring[j + 1];
399 if (j != 0) { /* Pole */
400 dest.append(sphere_lat_lon_vert(next_lat_pt, next_lon_pt));
401 dest.append(sphere_lat_lon_vert(next_lat_pt, lon_pt));
402 dest.append(sphere_lat_lon_vert(lat_pt, lon_pt));
403 }
404 if (j != longitude_half_ring.index_range().last(1)) { /* Pole */
405 dest.append(sphere_lat_lon_vert(lat_pt, next_lon_pt));
406 dest.append(sphere_lat_lon_vert(next_lat_pt, next_lon_pt));
407 dest.append(sphere_lat_lon_vert(lat_pt, lon_pt));
408 }
409 }
410 }
411}
412
414{
416
417 /* Armature Octahedron. */
418 {
420 for (int tri = 0; tri < 8; tri++) {
421 for (int v = 0; v < 3; v++) {
425 }
426 }
427 bone_octahedron = BatchPtr(
429 }
430 {
433
434 for (auto line : bone_octahedral_wire_lines_adjacency) {
435 GPU_indexbuf_add_line_adj_verts(&elb, line[0], line[1], line[2], line[3]);
436 }
438
439 /* NOTE: Reuses the same VBO as bone_octahedron. Thus has the same vertex format. */
442 }
443
444 /* Armature Sphere. */
445 {
446 constexpr int resolution = 64;
447 Vector<float2> ring = ring_vertices(0.05f, resolution);
448
450 for (int a : IndexRange(resolution + 1)) {
451 float2 cv = ring[a % resolution];
452 verts.append({{cv.x, cv.y, 0.0f}, VCLASS_EMPTY_SCALED});
453 }
454
457 }
458 {
459 bone_sphere_wire = BatchPtr(
460 GPU_batch_create(GPU_PRIM_LINE_STRIP, bone_sphere.get()->verts[0], nullptr));
461 }
462
463 /* Armature Stick. */
464 {
465 /* Gather as a strip and add to main buffer as a list of triangles. */
466 Vector<Vertex> vert_strip;
467 vert_strip.append({{0.0f, 1.0f, 0.0f}, COL_BONE | POS_BONE | POS_HEAD | COL_HEAD | COL_WIRE});
468 vert_strip.append({{0.0f, 1.0f, 0.0f}, COL_BONE | POS_BONE | POS_TAIL | COL_TAIL | COL_WIRE});
469 vert_strip.append({{0.0f, 0.0f, 0.0f}, COL_BONE | POS_BONE | POS_HEAD | COL_HEAD});
470 vert_strip.append({{0.0f, 0.0f, 0.0f}, COL_BONE | POS_BONE | POS_TAIL | COL_TAIL});
471 vert_strip.append({{0.0f, -1.0f, 0.0f}, COL_BONE | POS_BONE | POS_HEAD | COL_HEAD | COL_WIRE});
472 vert_strip.append({{0.0f, -1.0f, 0.0f}, COL_BONE | POS_BONE | POS_TAIL | COL_TAIL | COL_WIRE});
473
475 /* Bone rectangle */
476 for (int t : IndexRange(vert_strip.size() - 2)) {
477 /* NOTE: Don't care about winding.
478 * Theses triangles are facing the camera and should not be backface culled. */
479 verts.append(vert_strip[t]);
480 verts.append(vert_strip[t + 1]);
481 verts.append(vert_strip[t + 2]);
482 }
483
484 constexpr int resolution = 12;
485 Vector<float2> ring = ring_vertices(2.0f, resolution);
486 for (int a : IndexRange(resolution)) {
487 float2 cv1 = ring[a % resolution];
488 float2 cv2 = ring[(a + 1) % resolution];
489 /* Head point. */
490 verts.append({{0.0f, 0.0f, 0.0f}, int(POS_HEAD | COL_HEAD)});
491 verts.append({{cv1.x, cv1.y, 0.0f}, int(POS_HEAD | COL_HEAD | COL_WIRE)});
492 verts.append({{cv2.x, cv2.y, 0.0f}, int(POS_HEAD | COL_HEAD | COL_WIRE)});
493 /* Tail point. */
494 verts.append({{0.0f, 0.0f, 0.0f}, int(POS_TAIL | COL_TAIL)});
495 verts.append({{cv1.x, cv1.y, 0.0f}, int(POS_TAIL | COL_TAIL | COL_WIRE)});
496 verts.append({{cv2.x, cv2.y, 0.0f}, int(POS_TAIL | COL_TAIL | COL_WIRE)});
497 }
498
499 bone_stick = BatchPtr(
501 }
502
503 /* Armature BBones. */
504 {
506 for (int tri = 0; tri < 12; tri++) {
507 for (int v = 0; v < 3; v++) {
511 }
512 }
513 bone_box = BatchPtr(
515 }
516 {
519
520 for (auto line : bone_box_wire_lines_adjacency) {
521 GPU_indexbuf_add_line_adj_verts(&elb, line[0], line[1], line[2], line[3]);
522 }
524
525 /* NOTE: Reuses the same VBO as bone_box. Thus has the same vertex format. */
527 GPU_PRIM_LINES_ADJ, bone_box.get()->verts[0], ibo, GPU_BATCH_OWNS_INDEX));
528 }
529
530 /* Armature Envelope. */
531 {
532 constexpr int lon_res = 24;
533 constexpr int lat_res = 24;
534 constexpr float lon_inc = 2.0f * M_PI / lon_res;
535 constexpr float lat_inc = M_PI / lat_res;
536
537 auto lat_lon_to_co = [](const float lat, const float lon) {
538 return float3(sinf(lat) * cosf(lon), sinf(lat) * sinf(lon), cosf(lat));
539 };
540
542 float lon = 0.0f;
543 for (int i = 0; i < lon_res; i++, lon += lon_inc) {
544 float lat = 0.0f;
545 /* NOTE: the poles are duplicated on purpose, to restart the strip. */
546 for (int j = 0; j < lat_res; j++, lat += lat_inc) {
547 verts.append({lat_lon_to_co(lat, lon), VCLASS_NONE});
548 verts.append({lat_lon_to_co(lat, lon + lon_inc), VCLASS_NONE});
549 }
550 /* Closing the loop */
551 verts.append({lat_lon_to_co(M_PI, lon), VCLASS_NONE});
552 verts.append({lat_lon_to_co(M_PI, lon + lon_inc), VCLASS_NONE});
553 }
554
557 }
558 {
559 constexpr int circle_resolution = 64;
560 float2 v0, v1, v2;
561
562 auto circle_pt = [](const float angle) { return float2(sinf(angle), cosf(angle)); };
563
565 /* Output 3 verts for each position. See shader for explanation. */
566 v0 = circle_pt((2.0f * M_PI * -2) / float(circle_resolution));
567 v1 = circle_pt((2.0f * M_PI * -1) / float(circle_resolution));
568 for (int a = 0; a <= circle_resolution; a++, v0 = v1, v1 = v2) {
569 v2 = circle_pt((2.0f * M_PI * a) / float(circle_resolution));
570 verts.append({v0, v1, v2});
571 }
572
575 }
576
577 /* Degrees of freedom. */
578 {
579 constexpr int resolution = 16;
580
582 auto set_vert = [&](const float x, const float y, const int quarter) {
583 verts.append({{(quarter % 2 == 0) ? -x : x, (quarter < 2) ? -y : y, 0.0f}, VCLASS_NONE});
584 };
585
586 for (int quarter : IndexRange(4)) {
587 float prev_z = 0.0f;
588 for (int i : IndexRange(1, resolution - 1)) {
589 float z = sinf(M_PI_2 * i / float(resolution - 1));
590 float prev_x = 0.0f;
591 for (int j : IndexRange(1, resolution - i)) {
592 float x = sinf(M_PI_2 * j / float(resolution - 1));
593 if (j == resolution - i) {
594 /* Pole triangle. */
595 set_vert(prev_x, z, quarter);
596 set_vert(prev_x, prev_z, quarter);
597 set_vert(x, prev_z, quarter);
598 }
599 else {
600 /* Quad. */
601 set_vert(x, z, quarter);
602 set_vert(x, prev_z, quarter);
603 set_vert(prev_x, z, quarter);
604
605 set_vert(x, prev_z, quarter);
606 set_vert(prev_x, prev_z, quarter);
607 set_vert(prev_x, z, quarter);
608 }
609 prev_x = x;
610 }
611 prev_z = z;
612 }
613 }
614
615 bone_degrees_of_freedom = BatchPtr(
617 }
618 {
619 constexpr int resolution = 16 * 4;
620 Vector<float2> ring = ring_vertices(1.0f, resolution);
621
623 for (int a : IndexRange(resolution + 1)) {
624 float2 cv = ring[a % resolution];
625 verts.append({{cv.x, cv.y, 0.0f}, VCLASS_NONE});
626 }
627
630 }
631
632 /* quad_wire */
633 {
635 verts.append({{-1.0f, -1.0f, 0.0f}, VCLASS_EMPTY_SCALED});
636 verts.append({{-1.0f, +1.0f, 0.0f}, VCLASS_EMPTY_SCALED});
637 verts.append({{-1.0f, +1.0f, 0.0f}, VCLASS_EMPTY_SCALED});
638 verts.append({{+1.0f, +1.0f, 0.0f}, VCLASS_EMPTY_SCALED});
639 verts.append({{+1.0f, +1.0f, 0.0f}, VCLASS_EMPTY_SCALED});
640 verts.append({{+1.0f, -1.0f, 0.0f}, VCLASS_EMPTY_SCALED});
641 verts.append({{+1.0f, -1.0f, 0.0f}, VCLASS_EMPTY_SCALED});
642 verts.append({{-1.0f, -1.0f, 0.0f}, VCLASS_EMPTY_SCALED});
643
644 quad_wire = BatchPtr(
646 }
647 /* quad_solid */
648 {
649 const Array<float2> quad = {{-1.0f, 1.0f}, {1.0f, 1.0f}, {-1.0f, -1.0f}, {1.0f, -1.0f}};
651 for (const float2 &point : quad) {
653 }
656 }
657 /* plain_axes */
658 {
660 verts.append({{0.0f, -1.0f, 0.0f}, VCLASS_EMPTY_SCALED});
661 verts.append({{0.0f, +1.0f, 0.0f}, VCLASS_EMPTY_SCALED});
662 verts.append({{-1.0f, 0.0f, 0.0f}, VCLASS_EMPTY_SCALED});
663 verts.append({{+1.0f, 0.0f, 0.0f}, VCLASS_EMPTY_SCALED});
664 verts.append({{0.0f, 0.0f, -1.0f}, VCLASS_EMPTY_SCALED});
665 verts.append({{0.0f, 0.0f, +1.0f}, VCLASS_EMPTY_SCALED});
666
667 plain_axes = BatchPtr(
669 }
670 /* single_arrow */
671 {
673 float p[3][3] = {{0}};
674 p[0][2] = 1.0f;
675 p[1][0] = 0.035f;
676 p[1][1] = 0.035f;
677 p[2][0] = -0.035f;
678 p[2][1] = 0.035f;
679 p[1][2] = p[2][2] = 0.75f;
680 for (int sides : IndexRange(4)) {
681 if (sides % 2 == 1) {
682 p[1][0] = -p[1][0];
683 p[2][1] = -p[2][1];
684 }
685 else {
686 p[1][1] = -p[1][1];
687 p[2][0] = -p[2][0];
688 }
689 for (int i = 0, a = 1; i < 2; i++, a++) {
690 verts.append({{p[i][0], p[i][1], p[i][2]}, VCLASS_EMPTY_SCALED});
691 verts.append({{p[a][0], p[a][1], p[a][2]}, VCLASS_EMPTY_SCALED});
692 }
693 }
694 verts.append({{0.0f, 0.0f, 0.0}, VCLASS_EMPTY_SCALED});
695 verts.append({{0.0f, 0.0f, 0.75f}, VCLASS_EMPTY_SCALED});
696
697 single_arrow = BatchPtr(
699 }
700 /* cube */
701 {
703 for (auto index : bone_box_wire_lines) {
704 float x = bone_box_verts[index][0];
705 float y = bone_box_verts[index][1] * 2.0 - 1.0f;
706 float z = bone_box_verts[index][2];
708 }
709
710 cube = BatchPtr(
712 }
713 /* circle */
714 {
715 constexpr int resolution = 64;
716 Vector<float2> ring = ring_vertices(1.0f, resolution);
717
719 for (int a : IndexRange(resolution + 1)) {
720 float2 cv1 = ring[(a + 0) % resolution];
721 float2 cv2 = ring[(a + 1) % resolution];
722 verts.append({{cv1.x, 0.0f, cv1.y}, VCLASS_EMPTY_SCALED});
723 verts.append({{cv2.x, 0.0f, cv2.y}, VCLASS_EMPTY_SCALED});
724 }
725
726 circle = BatchPtr(
728 }
729 /* empty_spehere */
730 {
732
733 empty_sphere = BatchPtr(
735 }
736 /* empty_cone */
737 {
738 constexpr int resolution = 8;
739 Vector<float2> ring = ring_vertices(1.0f, resolution);
740
742 for (int i : IndexRange(resolution)) {
743 float2 cv = ring[i % resolution];
744 /* Cone sides. */
745 verts.append({{cv[0], 0.0f, cv[1]}, VCLASS_EMPTY_SCALED});
746 verts.append({{0.0f, 2.0f, 0.0f}, VCLASS_EMPTY_SCALED});
747 /* Base ring. */
748 for (int j : IndexRange(2)) {
749 float2 cv = ring[(i + j) % resolution];
750 verts.append({{cv[0], 0.0f, cv[1]}, VCLASS_EMPTY_SCALED});
751 }
752 }
753
754 empty_cone = BatchPtr(
756 }
757 /* cylinder */
758 {
759 constexpr int n_segments = 12;
760 const Vector<float2> ring = ring_vertices(1.0f, n_segments);
762 /* top ring */
764 /* bottom ring */
766 /* cylinder sides */
767 for (const float2 &point : ring) {
768 verts.append({{point.x, point.y, 1.0f}, VCLASS_EMPTY_SCALED});
769 verts.append({{point.x, point.y, -1.0f}, VCLASS_EMPTY_SCALED});
770 }
771 cylinder = BatchPtr(
773 }
774 /* capsule body */
775 {
776 const Vector<float2> diamond = ring_vertices(1.0f, 4);
778 for (const float2 &point : diamond) {
779 verts.append({{point.x, point.y, 1.0f}, VCLASS_NONE});
780 verts.append({{point.x, point.y, 0.0f}, VCLASS_NONE});
781 }
782 capsule_body = BatchPtr(
784 }
785 /* capsule cap */
786 {
787 constexpr int n_segments = 24;
788 const Vector<float2> ring = ring_vertices(1.0f, n_segments);
790 /* Base circle */
791 append_line_loop(verts, ring, 0.0f, VCLASS_NONE);
792 for (const int i : IndexRange(n_segments / 2)) {
793 const float2 &point = ring[i];
794 const float2 &next_point = ring[i + 1];
795 /* Y half circle */
796 verts.append({{point.x, 0.0f, point.y}, VCLASS_NONE});
797 verts.append({{next_point.x, 0.0f, next_point.y}, VCLASS_NONE});
798 /* X half circle */
799 verts.append({{0.0f, point.x, point.y}, VCLASS_NONE});
800 verts.append({{0.0f, next_point.x, next_point.y}, VCLASS_NONE});
801 }
802 capsule_cap = BatchPtr(
804 }
805 /* arrows */
806 {
807 float2 x_axis_name_scale = {0.0215f, 0.025f};
809 float2(0.9f, 1.0f) * x_axis_name_scale,
810 float2(-1.0f, -1.0f) * x_axis_name_scale,
811 float2(-0.9f, 1.0f) * x_axis_name_scale,
812 float2(1.0f, -1.0f) * x_axis_name_scale,
813 };
814
815 float2 y_axis_name_scale = {0.0175f, 0.025f};
817 float2(-1.0f, 1.0f) * y_axis_name_scale,
818 float2(0.0f, -0.1f) * y_axis_name_scale,
819 float2(1.0f, 1.0f) * y_axis_name_scale,
820 float2(0.0f, -0.1f) * y_axis_name_scale,
821 float2(0.0f, -0.1f) * y_axis_name_scale,
822 float2(0.0f, -1.0f) * y_axis_name_scale,
823 };
824
825 float2 z_axis_name_scale = {0.02f, 0.025f};
827 float2(-0.95f, 1.00f) * z_axis_name_scale,
828 float2(0.95f, 1.00f) * z_axis_name_scale,
829 float2(0.95f, 1.00f) * z_axis_name_scale,
830 float2(0.95f, 0.90f) * z_axis_name_scale,
831 float2(0.95f, 0.90f) * z_axis_name_scale,
832 float2(-1.00f, -0.90f) * z_axis_name_scale,
833 float2(-1.00f, -0.90f) * z_axis_name_scale,
834 float2(-1.00f, -1.00f) * z_axis_name_scale,
835 float2(-1.00f, -1.00f) * z_axis_name_scale,
836 float2(1.00f, -1.00f) * z_axis_name_scale,
837 };
838
839 float2 axis_marker_scale = {0.007f, 0.007f};
841#if 0 /* square */
842 float2(-1.0f, 1.0f) * axis_marker_scale,
843 float2(1.0f, 1.0f) * axis_marker_scale,
844 float2(1.0f, 1.0f) * axis_marker_scale,
845 float2(1.0f, -1.0f) * axis_marker_scale,
846 float2(1.0f, -1.0f) * axis_marker_scale,
847 float2(-1.0f, -1.0f) * axis_marker_scale,
848 float2(-1.0f, -1.0f) * axis_marker_scale,
849 float2(-1.0f, 1.0f) * axis_marker_scale,
850#else /* diamond */
851 float2(-1.0f, 0.0f) * axis_marker_scale,
852 float2(0.0f, 1.0f) * axis_marker_scale,
853 float2(0.0f, 1.0f) * axis_marker_scale,
854 float2(1.0f, 0.0f) * axis_marker_scale,
855 float2(1.0f, 0.0f) * axis_marker_scale,
856 float2(0.0f, -1.0f) * axis_marker_scale,
857 float2(0.0f, -1.0f) * axis_marker_scale,
858 float2(-1.0f, 0.0f) * axis_marker_scale,
859#endif
860 };
861
863 for (int axis : IndexRange(3)) {
864 /* Vertex layout is XY screen position and axis in Z.
865 * Fractional part of Z is a positive offset at axis unit position. */
867 /* Center to axis line. */
868 verts.append({{0.0f, 0.0f, 0.0f}, 0});
869 verts.append({{0.0f, 0.0f, float(axis)}, flag});
870 /* Axis end marker. */
871 constexpr int marker_fill_layer = 6;
872 for (int j = 1; j < marker_fill_layer + 1; j++) {
873 for (float2 axis_marker_vert : axis_marker) {
874 verts.append({{axis_marker_vert * ((4.0f * j) / marker_fill_layer), float(axis)}, flag});
875 }
876 }
877 /* Axis name. */
878 const Vector<float2> *axis_names[3] = {&x_axis_name, &y_axis_name, &z_axis_name};
879 for (float2 axis_name_vert : *(axis_names[axis])) {
881 verts.append({{axis_name_vert * 4.0f, axis + 0.25f}, flag});
882 }
883 }
884 arrows = BatchPtr(
886 }
887 /* metaball_wire_circle */
888 {
889 constexpr int resolution = 64;
890 constexpr float radius = 1.0f;
891 Vector<float2> ring = ring_vertices(radius, resolution);
892
894 for (int i : IndexRange(resolution + 1)) {
895 float2 cv = ring[i % resolution];
896 verts.append({{cv[0], cv[1], 0.0f}, VCLASS_SCREENALIGNED});
897 }
900 };
901 /* speaker */
902 {
903 constexpr int segments = 16;
904 constexpr float bottom_r = 0.5f;
905 constexpr float bottom_z = -0.125f;
906 constexpr float step_z = 0.25f;
907 const Vector<float2> diamond = ring_vertices(bottom_r, 4);
908 Vector<float2> ring = ring_vertices(bottom_r, segments);
910
911 append_line_loop(verts, ring, bottom_z, VCLASS_NONE);
912 for (float2 &point : ring) {
913 point *= 0.5f;
914 }
915 for (const int j : IndexRange(1, 2)) {
916 const float z = step_z * j + bottom_z;
918 }
919
920 for (const float2 &point : diamond) {
921 Vertex vertex{float3(point, bottom_z)};
922 verts.append(vertex);
923 vertex.pos = float3(point * 0.5f, bottom_z + step_z);
924 verts.append(vertex);
925 verts.append(vertex);
926 vertex.pos.z += step_z;
927 verts.append(vertex);
928 }
929 speaker = BatchPtr(
931 }
932 /* camera distances */
933 {
934 const Vector<float2> diamond = ring_vertices(1.5f, 5);
935 const Vector<float2> cross = {{1.0f, 0.0f}, {-1.0f, 0.0f}, {0.0f, 1.0f}, {0.0f, -1.0f}};
936
938 verts.append({{0.0f, 0.0f, 0.0f}, VCLASS_CAMERA_DIST});
939 verts.append({{0.0f, 0.0f, 1.0f}, VCLASS_CAMERA_DIST});
940
943
944 /* Focus cross */
945 for (const float2 &point : cross) {
946 verts.append({{point.x, point.y, 2.0f}, VCLASS_CAMERA_DIST});
947 }
948 camera_distances = BatchPtr(
950 }
951 /* camera frame */
952 {
953 const Vector<float2> rect{{-1.0f, -1.0f}, {-1.0f, 1.0f}, {1.0f, 1.0f}, {1.0f, -1.0f}};
955 /* Frame */
957 /* Wires to origin. */
958 for (const float2 &point : rect) {
959 verts.append({{point.x, point.y, 1.0f}, VCLASS_CAMERA_FRAME});
960 verts.append({{point.x, point.y, 0.0f}, VCLASS_CAMERA_FRAME});
961 }
962 camera_frame = BatchPtr(
964 }
965 /* camera tria */
966 {
967 const Vector<float2> triangle = {{-1.0f, 1.0f}, {1.0f, 1.0f}, {0.0f, 0.0f}};
968 Vector<Vertex> verts(2 * 3);
969 /* Wire */
971 camera_tria_wire = BatchPtr(
973
974 verts.clear();
975 /* Triangle */
976 for (const float2 &point : triangle) {
977 verts.append({{point.x, point.y, 1.0f}, VCLASS_CAMERA_FRAME});
978 }
979 camera_tria = BatchPtr(
981 }
982 /* camera volume */
983 {
985 for (const uint3 &tri : bone_box_solid_tris) {
986 for (const int i : IndexRange(tri.type_length)) {
987 const int v = tri[i];
988 const float x = bone_box_verts[v][2];
989 const float y = bone_box_verts[v][0];
990 const float z = bone_box_verts[v][1];
992 }
993 }
994 camera_volume = BatchPtr(
996 }
997 /* camera volume wire */
998 {
1000 for (int i : bone_box_wire_lines) {
1001 const float x = bone_box_verts[i][2];
1002 const float y = bone_box_verts[i][0];
1003 const float z = bone_box_verts[i][1];
1005 }
1006 camera_volume_wire = BatchPtr(
1008 }
1009 /* spheres */
1010 {
1013 sphere_low_detail = BatchPtr(
1015 }
1016 /* ground line */
1017 {
1018 const Vector<float2> ring = ring_vertices(1.35f, diamond_nsegments);
1019
1021 /* Ground Point */
1022 append_line_loop(verts, ring, 0.0f, 0);
1023 /* Ground Line */
1024 verts.append({{0.0, 0.0, 1.0}, 0});
1025 verts.append({{0.0, 0.0, 0.0}, 0});
1026
1027 ground_line = BatchPtr(
1029 }
1030 /* light spot volume */
1031 {
1033
1034 /* Cone apex */
1035 verts.append({{0.0f, 0.0f, 0.0f}, 0});
1036 /* Cone silhouette */
1037 for (const int angle_i : IndexRange(circle_nsegments + 1)) {
1038 const float angle = (2.0f * math::numbers::pi * angle_i) / circle_nsegments;
1039 const float s = sinf(-angle);
1040 const float c = cosf(-angle);
1041 verts.append({{s, c, -1.0f}, VCLASS_LIGHT_SPOT_SHAPE});
1042 }
1045 }
1046 /* light icon outer lines */
1047 {
1048 constexpr float r = 9.0f;
1049 const Vector<float2> ring = ring_vertices(r * 1.33f, outer_nsegments * 2);
1050
1052 append_line_loop(verts, ring, 0.0f, VCLASS_SCREENSPACE, true);
1053 light_icon_outer_lines = BatchPtr(
1055 }
1056 /* light icon inner lines */
1057 {
1058 constexpr float r = 9.0f;
1059 const Vector<float2> diamond = ring_vertices(r * 0.3f, diamond_nsegments);
1060 const Vector<float2> ring = ring_vertices(r, inner_nsegments * 2);
1061
1063 append_line_loop(verts, diamond, 0.0f, VCLASS_SCREENSPACE);
1064 append_line_loop(verts, ring, 0.0f, VCLASS_SCREENSPACE, true);
1065
1066 light_icon_inner_lines = BatchPtr(
1068 }
1069 /* light icon sun rays */
1070 {
1071 constexpr int num_rays = 8;
1072 constexpr float r = 9.0f;
1073 const Vector<float2> ring = ring_vertices(r, num_rays);
1074 const std::array<float, 4> scales{1.6f, 1.9f, 2.2f, 2.5f};
1075
1077 for (const float2 &point : ring) {
1078 for (float scale : scales) {
1079 float2 scaled = point * scale;
1080 verts.append({{scaled.x, scaled.y, 0.0f}, VCLASS_SCREENSPACE});
1081 }
1082 }
1083 light_icon_sun_rays = BatchPtr(
1085 }
1086 /* light point lines */
1087 {
1088 const Vector<float2> ring = ring_vertices(1.0f, circle_nsegments);
1089
1092 light_point_lines = BatchPtr(
1094 }
1095 /* light sun lines */
1096 {
1098 /* Direction Line */
1099 verts.append({{0.0, 0.0, 0.0}, 0});
1100 verts.append({{0.0, 0.0, -20.0}, 0}); /* Good default. */
1101 light_sun_lines = BatchPtr(
1103 }
1104 /* light spot lines */
1105 {
1106 const Vector<float2> ring = ring_vertices(1.0f, circle_nsegments);
1107
1109 /* Light area */
1111 /* Cone cap */
1114 /* Cone silhouette */
1115 for (const float2 &point : ring) {
1116 verts.append({{0.0f, 0.0f, 0.0f}, 0});
1117 verts.append({{point.x, point.y, -1.0f}, VCLASS_LIGHT_SPOT_SHAPE | VCLASS_LIGHT_SPOT_CONE});
1118 }
1119
1121
1122 light_spot_lines = BatchPtr(
1124 }
1125 /* light area disk lines */
1126 {
1127 const Vector<float2> ring = ring_vertices(0.5f, circle_nsegments);
1128
1130 /* Light area */
1132
1134
1135 light_area_disk_lines = BatchPtr(
1137 }
1138 /* light area square lines */
1139 {
1140 const Array<float2> rect{{-0.5f, -0.5f}, {-0.5f, 0.5f}, {0.5f, 0.5f}, {0.5f, -0.5f}};
1141
1143 /* Light area */
1145
1147
1148 light_area_square_lines = BatchPtr(
1150 }
1151 /* field_force */
1152 {
1153 constexpr int circle_resol = 32;
1155 constexpr std::array<float, 2> scales{2.0f, 0.75};
1156 Vector<float2> ring = ring_vertices(1.0f, circle_resol);
1157
1159
1160 append_line_loop(verts, ring, 0.0f, flag);
1161 for (const float scale : scales) {
1162 for (float2 &point : ring) {
1163 point *= scale;
1164 }
1165 append_line_loop(verts, ring, 0.0f, flag);
1166 }
1167
1168 field_force = BatchPtr(
1170 }
1171 /* field_wind */
1172 {
1173 constexpr int circle_resol = 32;
1174 const Vector<float2> ring = ring_vertices(1.0f, circle_resol);
1175
1177
1178 for (const int i : IndexRange(4)) {
1179 const float z = 0.05f * float(i);
1181 }
1182
1183 field_wind = BatchPtr(
1185 }
1186 /* field_vortex */
1187 {
1188 constexpr int spiral_resol = 32;
1189 const Vector<float2> ring = ring_vertices(1.0f, spiral_resol);
1190
1192
1193 for (const int i : IndexRange(ring.size() * 2 + 1)) {
1194 /* r: [-1, .., 0, .., 1] */
1195 const float r = (i - spiral_resol) / float(spiral_resol);
1196 /* index: [9, spiral_resol - 1, spiral_resol - 2, .., 2, 1, 0, 1, 2, .., spiral_resol - 1, 0]
1197 */
1198 const float2 point = ring[abs(spiral_resol - i) % spiral_resol] * r;
1199 verts.append({float3(point.y, point.x, 0.0f), VCLASS_EMPTY_SIZE});
1200 }
1203 }
1204 /* field_curve */
1205 {
1206 constexpr int circle_resol = 32;
1207 const Vector<float2> ring = ring_vertices(1.0f, circle_resol);
1208
1210
1212
1213 field_curve = BatchPtr(
1215 }
1216 /* field_sphere_limit */
1217 {
1218 constexpr int circle_resol = 32 * 2;
1219 const Vector<float2> ring = ring_vertices(1.0f, circle_resol);
1220
1222
1224
1225 field_sphere_limit = BatchPtr(
1227 }
1228 /* field_tube_limit */
1229 {
1230 constexpr int circle_resol = 32;
1231 constexpr int side_stipple = 32;
1232 const Vector<float2> ring = ring_vertices(1.0f, circle_resol);
1233 const Vector<float2> diamond = ring_vertices(1.0f, 4);
1234
1236
1237 /* Caps */
1238 for (const int i : IndexRange(2)) {
1239 const float z = i * 2.0f - 1.0f;
1241 }
1242 /* Side Edges */
1243 for (const float2 &point : diamond) {
1244 for (const int i : IndexRange(side_stipple)) {
1245 const float z = (i / float(side_stipple)) * 2.0f - 1.0f;
1246 verts.append({float3(point.y, point.x, z), VCLASS_EMPTY_SIZE});
1247 }
1248 }
1249
1250 field_tube_limit = BatchPtr(
1252 }
1253 /* field_cone_limit */
1254 {
1255 constexpr int circle_resol = 32;
1256 constexpr int side_stipple = 32;
1257 const Vector<float2> ring = ring_vertices(1.0f, circle_resol);
1258 const Vector<float2> diamond = ring_vertices(1.0f, 4);
1259
1261
1262 /* Caps */
1263 for (const int i : IndexRange(2)) {
1264 const float z = i * 2.0f - 1.0f;
1266 }
1267 /* Side Edges */
1268 for (const float2 &point : diamond) {
1269 for (const int i : IndexRange(side_stipple)) {
1270 const float z = (i / float(side_stipple)) * 2.0f - 1.0f;
1271 verts.append({float3(point.y * z, point.x * z, z), VCLASS_EMPTY_SIZE});
1272 }
1273 }
1274
1275 field_cone_limit = BatchPtr(
1277 }
1278 /* lightprobe_cube */
1279 {
1280 constexpr float r = 14.0f;
1281 constexpr int flag = VCLASS_SCREENSPACE;
1282 /* Icon */
1283 constexpr float sin_pi_3 = 0.86602540378f;
1284 constexpr float cos_pi_3 = 0.5f;
1285 const Array<float2, 6> points = {
1286 float2(0.0f, 1.0f) * r,
1287 float2(sin_pi_3, cos_pi_3) * r,
1288 float2(sin_pi_3, -cos_pi_3) * r,
1289 float2(0.0f, -1.0f) * r,
1290 float2(-sin_pi_3, -cos_pi_3) * r,
1291 float2(-sin_pi_3, cos_pi_3) * r,
1292 };
1293
1295
1296 append_line_loop(verts, points, 0.0f, flag);
1297 for (const int i : IndexRange(3)) {
1298 const float2 &point = points[i * 2 + 1];
1299 verts.append(Vertex{{point, 0.0f}, flag});
1300 verts.append(Vertex{{0.0f, 0.0f, 0.0f}, flag});
1301 }
1302
1303 /* Direction Lines */
1304 const Vector<float2> diamond = ring_vertices(1.2f, diamond_nsegments);
1305 const std::string axes = "zZyYxX";
1306 for (const char axis : axes) {
1307 light_append_direction_line(axis, diamond, verts);
1308 }
1309
1310 lightprobe_cube = BatchPtr(
1312 }
1313 /* lightprobe_planar */
1314 {
1315 constexpr float r = 20.0f;
1316 /* Icon */
1317 constexpr float sin_pi_3 = 0.86602540378f;
1318 const Array<float2, 4> points = {
1319 float2(0.0f, 0.5f) * r,
1320 float2(sin_pi_3, 0.0f) * r,
1321 float2(0.0f, -0.5f) * r,
1322 float2(-sin_pi_3, 0.0f) * r,
1323 };
1324
1326
1328 lightprobe_planar = BatchPtr(
1330 }
1331 /* lightprobe_grid */
1332 {
1333 constexpr float r = 14.0f;
1334 constexpr int flag = VCLASS_SCREENSPACE;
1335 /* Icon */
1336 constexpr float sin_pi_3 = 0.86602540378f;
1337 constexpr float cos_pi_3 = 0.5f;
1338 const Array<float2, 6> points = {float2(0.0f, 1.0f) * r,
1339 float2(sin_pi_3, cos_pi_3) * r,
1340 float2(sin_pi_3, -cos_pi_3) * r,
1341 float2(0.0f, -1.0f) * r,
1342 float2(-sin_pi_3, -cos_pi_3) * r,
1343 float2(-sin_pi_3, cos_pi_3) * r};
1345
1346 append_line_loop(verts, points, 0.0f, flag);
1347 /* Internal wires. */
1348 for (const int i : IndexRange(6)) {
1349 const float2 tr = points[(i / 2) * 2 + 1] * -0.5f;
1350 const float2 t1 = points[i] + tr;
1351 const float2 t2 = points[(i + 1) % 6] + tr;
1352 verts.append({{t1, 0.0f}, flag});
1353 verts.append({{t2, 0.0f}, flag});
1354 }
1355 for (const int i : IndexRange(3)) {
1356 const float2 &point = points[i * 2 + 1];
1357 verts.append(Vertex{{point, 0.0f}, flag});
1358 verts.append(Vertex{{0.0f, 0.0f, 0.0f}, flag});
1359 }
1360 /* Direction Lines */
1361 const Vector<float2> diamond = ring_vertices(1.2f, diamond_nsegments);
1362 const std::string axes = "zZyYxX";
1363 for (const char axis : axes) {
1364 light_append_direction_line(axis, diamond, verts);
1365 }
1366
1367 lightprobe_grid = BatchPtr(
1369 }
1370 /* grid */
1371 {
1372 constexpr int resolution = 8;
1373 std::array<float, resolution + 1> steps;
1374 /* [-1, 1] divided into "resolution" steps. */
1375 for (const int i : IndexRange(resolution + 1)) {
1376 steps[i] = -1.0f + float(i * 2) / resolution;
1377 }
1378
1380 verts.reserve(resolution * resolution * 6);
1381 for (const int x : IndexRange(resolution)) {
1382 for (const int y : IndexRange(resolution)) {
1383 verts.append(Vertex{{steps[x], steps[y], 0.0f}});
1384 verts.append(Vertex{{steps[x + 1], steps[y], 0.0f}});
1385 verts.append(Vertex{{steps[x], steps[y + 1], 0.0f}});
1386
1387 verts.append(Vertex{{steps[x], steps[y + 1], 0.0f}});
1388 verts.append(Vertex{{steps[x + 1], steps[y], 0.0f}});
1389 verts.append(Vertex{{steps[x + 1], steps[y + 1], 0.0f}});
1390 }
1391 }
1392 grid = BatchPtr(
1394 }
1395}
1396
1397} // namespace blender::draw::overlay
#define BLI_assert(a)
Definition BLI_assert.h:50
#define M_PI_2
#define M_SQRT1_2
#define M_PI
#define UNUSED_VARS(...)
blender::gpu::Batch * GPU_batch_create_ex(GPUPrimType primitive_type, blender::gpu::VertBuf *vertex_buf, blender::gpu::IndexBuf *index_buf, eGPUBatchFlag owns_flag)
Definition gpu_batch.cc:56
#define GPU_batch_create(primitive_type, vertex_buf, index_buf)
Definition GPU_batch.hh:149
@ GPU_BATCH_OWNS_INDEX
Definition GPU_batch.hh:51
@ GPU_BATCH_OWNS_VBO
Definition GPU_batch.hh:42
void GPU_indexbuf_init(GPUIndexBufBuilder *, GPUPrimType, uint prim_len, uint vertex_len)
blender::gpu::IndexBuf * GPU_indexbuf_build(GPUIndexBufBuilder *)
void GPU_indexbuf_add_line_adj_verts(GPUIndexBufBuilder *, uint v1, uint v2, uint v3, uint v4)
@ GPU_PRIM_TRI_FAN
@ GPU_PRIM_LINES
@ GPU_PRIM_LINES_ADJ
@ GPU_PRIM_LINE_STRIP
@ GPU_PRIM_TRI_STRIP
@ GPU_PRIM_TRIS
#define GPU_vertbuf_create_with_format(format)
void GPU_vertbuf_data_alloc(blender::gpu::VertBuf &verts, uint v_len)
@ GPU_FETCH_FLOAT
@ GPU_FETCH_INT
uint GPU_vertformat_attr_add(GPUVertFormat *, const char *name, GPUVertCompType, uint comp_len, GPUVertFetchMode)
@ GPU_COMP_F32
@ GPU_COMP_I32
static double angle(const Eigen::Vector3d &v1, const Eigen::Vector3d &v2)
Definition IK_Math.h:125
in reality light always falls off quadratically Particle Retrieve the data of the particle that spawned the object for example to give variation to multiple instances of an object Point Retrieve information about points in a point cloud Retrieve the edges of an object as it appears to Cycles topology will always appear triangulated Convert a blackbody temperature to an RGB value Normal Generate a perturbed normal from an RGB normal map image Typically used for faking highly detailed surfaces Generate an OSL shader from a file or text data block Image Sample an image file as a texture Gabor Generate Gabor noise Gradient Generate interpolated color and intensity values based on the input vector Magic Generate a psychedelic color texture Voronoi Generate Worley noise based on the distance to random points Typically used to generate textures such as or biological cells Brick Generate a procedural texture producing bricks Texture Retrieve multiple types of texture coordinates nTypically used as inputs for texture nodes Vector Convert a point
ATTR_WARN_UNUSED_RESULT const BMVert * v2
ATTR_WARN_UNUSED_RESULT const BMVert * v
btMatrix3x3 scaled(const btVector3 &s) const
Create a scaled copy of the matrix.
SIMD_FORCE_INLINE const btScalar & z() const
Return the z value.
Definition btQuadWord.h:117
constexpr int64_t last(const int64_t n=0) const
int64_t size() const
void append(const T &value)
IndexRange index_range() const
void reserve(const int64_t min_capacity)
MutableSpan< T > data()
Definition half.h:42
#define sinf(x)
#define cosf(x)
#define set_vert(a, b, quarter)
static float y_axis_name[6][2]
static float x_axis_name[4][2]
#define COL_HEAD
#define POS_TAIL
#define COL_WIRE
static float z_axis_name[10][2]
#define POS_HEAD
#define COL_BONE
#define COL_TAIL
#define POS_BONE
static float axis_marker[8][2]
eDRWLevelOfDetail
Definition draw_cache.hh:32
@ DRW_LOD_LOW
Definition draw_cache.hh:33
@ DRW_LOD_MAX
Definition draw_cache.hh:37
draw_view in_light_buf[] float
draw_view push_constant(Type::INT, "radiance_src") .push_constant(Type capture_info_buf storage_buf(1, Qualifier::READ, "ObjectBounds", "bounds_buf[]") .push_constant(Type draw_view int
static float verts[][3]
blender::gpu::Batch * quad
format
static const std::array< uint3, 12 > bone_box_solid_tris
static const std::array< float3, 12 > bone_box_solid_normals
static constexpr int circle_nsegments
static Vector< float2 > ring_vertices(const float radius, const int segments, const bool half=false)
static const float bone_octahedral_solid_normals[8][3]
static const std::array< float3, 6 > bone_octahedral_verts
static float light_distance_z_get(char axis, const bool start)
static constexpr int inner_nsegments
static constexpr float bone_box_verts[8][3]
static constexpr int diamond_nsegments
static const std::array< uint3, 8 > bone_octahedral_solid_tris
static const std::array< float3, 6 > bone_octahedral_smooth_normals
static const std::array< uint2, 12 > bone_octahedral_wire_lines
static gpu::VertBuf * vbo_from_vector(const Vector< Vertex > &vector)
static void light_append_direction_line(const char axis, Span< float2 > diamond, Vector< Vertex > &verts)
static void append_line_loop(Vector< Vertex > &dest, Span< float2 > verts, float z, int flag, bool dashed=false)
static void append_sphere(Vector< VertShaded > &dest, const eDRWLevelOfDetail level_of_detail)
static constexpr std::array< uint, 24 > bone_box_wire_lines
static VertShaded sphere_lat_lon_vert(const float2 &lat_pt, const float2 &lon_pt)
static const std::array< uint4, 12 > bone_box_wire_lines_adjacency
static Vector< Vertex > sphere_axes_circles(const float radius, const VertexClass vclass, const int segments)
static constexpr int outer_nsegments
static const std::array< uint4, 12 > bone_octahedral_wire_lines_adjacency
T cos(const AngleRadianBase< T > &a)
MatBase< T, NumCol, NumRow > scale(const MatBase< T, NumCol, NumRow > &mat, const VectorT &scale)
T step(const T &edge, const T &value)
AxisSigned cross(const AxisSigned a, const AxisSigned b)
T sin(const AngleRadianBase< T > &a)
T abs(const T &a)
VecBase< float, 2 > float2
VecBase< float, 3 > float3
static const int steps
uint8_t flag
Definition wm_window.cc:138