Visual Computing Library  devel
Loading...
Searching...
No Matches
lines.h
1/*****************************************************************************
2 * VCLib *
3 * Visual Computing Library *
4 * *
5 * Copyright(C) 2021-2025 *
6 * Visual Computing Lab *
7 * ISTI - Italian National Research Council *
8 * *
9 * All rights reserved. *
10 * *
11 * This program is free software; you can redistribute it and/or modify *
12 * it under the terms of the Mozilla Public License Version 2.0 as published *
13 * by the Mozilla Foundation; either version 2 of the License, or *
14 * (at your option) any later version. *
15 * *
16 * This program is distributed in the hope that it will be useful, *
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
19 * Mozilla Public License Version 2.0 *
20 * (https://www.mozilla.org/en-US/MPL/2.0/) for more details. *
21 ****************************************************************************/
22
23#ifndef VCL_BGFX_PRIMITIVES_LINES_H
24#define VCL_BGFX_PRIMITIVES_LINES_H
25
26#include <vclib/bgfx/primitives/lines/cpu_generated_lines.h>
27#include <vclib/bgfx/primitives/lines/primitive_lines.h>
28#include <vclib/bgfx/uniform.h>
29
30#include <vclib/base.h>
31#include <vclib/space/core.h>
32
33#include <variant>
34
35#include <bgfx/bgfx.h>
36
37namespace vcl {
38
39// TODO: add shading per-line (flat, per-line normal) (?)
55class Lines
56{
57public:
58 enum class ColorToUse {
59 PER_VERTEX, // Select color form vertex color
60 PER_EDGE, // Select color from edge buffer color
61 GENERAL // Use general color in uniform data
62 };
63
64 enum class ImplementationType {
65 PRIMITIVE = 0, // Use bgfx primitive lines (not implemented)
66 CPU_GENERATED = 1, // Buffers pre-generated in CPU
67
68 // TODO: uncomment when they will be implemented
69 // GPU_GENERATED, // Buffers pre-generated in GPU with computes
70 // CPU_INSTANCING, // Using Instancing with buffers generated in CPU
71 // GPU_INSTANCING, // Using Instancing with buffer generated in GPU
72 // // computes
73 // TEXTURE_INSTANCING, // Using Instancing with textures generated in
74 // GPU computes
75
76 COUNT
77 };
78
79private:
80 float mThickness = 5.0f;
81
82 // TODO: shading should become a enum with options: PER_VERTEX, PER_EDGE,
83 // NONE
84 // PER_EDGE means that we use a buffer of normals for each edge
85 bool mShadingPerVertexCapability = false; // true if normals provided
86 bool mShadingPerVertex = false;
87
88 BitSet8 mColorCapability = {false, false, true}; // general color only
89 ColorToUse mColorToUse = ColorToUse::GENERAL;
90 Color mGeneralColor = Color::ColorABGR::LightGray;
91
92 ImplementationType mType = ImplementationType::COUNT;
93
94 Uniform mSettingUH = Uniform("u_settings", bgfx::UniformType::Vec4);
95 std::variant<detail::PrimitiveLines, detail::CPUGeneratedLines>
96 mLinesImplementation;
97
98public:
111 Lines(ImplementationType type = ImplementationType::COUNT)
112 {
113 if (type == ImplementationType::COUNT)
114 type = defaultImplementationType(false);
115 setImplementationType(type);
116 };
117
149 const std::vector<float>& vertCoords,
150 const std::vector<float>& vertNormals,
151 const std::vector<uint>& vertColors,
152 const std::vector<uint>& lineColors,
153 float thickness = 5.0f,
154 bool shadingPerVertex = false,
155 ColorToUse colorToUse = ColorToUse::GENERAL,
156 ImplementationType type = ImplementationType::COUNT) :
157 mThickness(thickness)
158 {
162 }
163
196 const std::vector<float>& vertCoords,
197 const std::vector<uint>& lineIndices,
198 const std::vector<float>& vertNormals,
199 const std::vector<uint>& vertColors,
200 const std::vector<uint>& lineColors,
201 float thickness = 5.0f,
202 bool shadingPerVertex = false,
203 ColorToUse colorToUse = ColorToUse::GENERAL,
204 ImplementationType type = ImplementationType::COUNT) :
205 mThickness(thickness)
206 {
207 setPoints(
211 }
212
237 const std::vector<float>& vertCoords,
238 const std::vector<float>& vertNormals,
239 const std::vector<uint>& vertColors,
240 const std::vector<uint>& lineColors,
241 ImplementationType type = ImplementationType::COUNT)
242 {
243 using enum ImplementationType;
244 using namespace detail;
245
246 if (type == COUNT)
247 type = defaultImplementationType(true);
248 setImplementationType(type);
249
250 switch (mType) {
251 case PRIMITIVE: // always supported
252 std::get<PrimitiveLines>(mLinesImplementation)
254 break;
255
256 case CPU_GENERATED: // always supported
257 std::get<CPUGeneratedLines>(mLinesImplementation)
259 break;
260 default: break;
261 }
262 updateShadingCapability(vertNormals);
263 updateColorCapability(vertColors, lineColors);
264 }
265
291 const std::vector<float>& vertCoords,
292 const std::vector<uint>& lineIndices,
293 const std::vector<float>& vertNormals,
294 const std::vector<uint>& vertColors,
295 const std::vector<uint>& lineColors,
296 ImplementationType type = ImplementationType::COUNT)
297 {
298 using enum ImplementationType;
299 using namespace detail;
300
301 if (type == COUNT)
302 type = defaultImplementationType(true);
303 setImplementationType(type);
304
305 switch (mType) {
306 case PRIMITIVE: // always supported
307 std::get<PrimitiveLines>(mLinesImplementation)
308 .setPoints(
313 lineColors);
314 break;
315
316 case CPU_GENERATED: // always supported
317 std::get<CPUGeneratedLines>(mLinesImplementation)
318 .setPoints(
323 lineColors);
324 break;
325 default: break;
326 }
327 updateShadingCapability(vertNormals);
328 updateColorCapability(vertColors, lineColors);
329 }
330
335 float thickness() const { return mThickness; }
336
342 float& thickness() { return mThickness; }
343
349 bool shadingPerVertex() const { return mShadingPerVertex; }
350
355 ColorToUse colorToUse() const { return mColorToUse; }
356
362 Color generalColor() const { return mGeneralColor; }
363
371 Color& generalColor() { return mGeneralColor; }
372
379 ImplementationType implementationType() const { return mType; }
380
392 {
393 if (!mShadingPerVertexCapability && perVertex) {
394 throw std::runtime_error(
395 "Lines::setShading(): shading per vertex not supported by the "
396 "current buffers.");
397 }
398 else {
399 mShadingPerVertex = perVertex;
400 }
401 }
402
411 void setColorToUse(ColorToUse color)
412 {
413 if (!mColorCapability[toUnderlying(color)]) {
414 throw std::runtime_error(
415 "Lines::setColorToUse(): color option not supported by the "
416 "current buffers.");
417 }
418 else {
419 mColorToUse = color;
420 }
421 }
422
427 void draw(uint viewId) const
428 {
429 using enum ImplementationType;
430 using namespace detail;
431
432 bindSettingsUniform();
433 if (mType == PRIMITIVE)
434 std::get<PrimitiveLines>(mLinesImplementation).draw(viewId);
435
436 if (mType == CPU_GENERATED)
437 std::get<CPUGeneratedLines>(mLinesImplementation).draw(viewId);
438 }
439
440private:
448 ImplementationType defaultImplementationType(
449 bool cpuMemPointsProvided) const
450 {
451 using enum ImplementationType;
452
454 return CPU_GENERATED;
455 else
456 return PRIMITIVE;
457 }
458
459 bool setImplementationType(ImplementationType type)
460 {
461 using enum ImplementationType;
462
463 if (mType == type)
464 return false; // no change
465
466 // TODO: check whether caps allow the new implementation type
467 // then set the implementation and the type
468 switch (type) {
469 case PRIMITIVE: // always supported
470 mLinesImplementation = detail::PrimitiveLines();
471 mType = type;
472 return true;
473
474 case CPU_GENERATED: // always supported
475 mLinesImplementation = detail::CPUGeneratedLines();
476 mType = type;
477 return true;
478
479 default: return false; // not supported
480 }
481 }
482
483 void updateShadingCapability(const std::vector<float>& vertNormals)
484 {
485 mShadingPerVertexCapability = !vertNormals.empty();
486 if (!mShadingPerVertexCapability)
487 mShadingPerVertex = false;
488 }
489
490 void updateColorCapability(
491 const std::vector<uint>& vertColors,
492 const std::vector<uint>& lineColors)
493 {
494 using enum ColorToUse;
495
496 mColorCapability[toUnderlying(PER_VERTEX)] = !vertColors.empty();
497 mColorCapability[toUnderlying(PER_EDGE)] = !lineColors.empty();
498
499 if (!mColorCapability[toUnderlying(mColorToUse)])
500 mColorToUse = GENERAL;
501 }
502
503 void bindSettingsUniform() const
504 {
505 float data[] = {
506 mThickness,
507 static_cast<float>(mColorToUse),
508 std::bit_cast<float>(mGeneralColor.abgr()),
509 static_cast<float>(mShadingPerVertex)};
510 mSettingUH.bind(data);
511 }
512};
513
514} // namespace vcl
515
516#endif // VCL_BGFX_PRIMITIVES_LINES_H
A class representing a box in N-dimensional space.
Definition box.h:46
The Color class represents a 32 bit color.
Definition color.h:48
The Lines class provides an abstraction for rendering 3D lines with variable thickness and different ...
Definition lines.h:56
ImplementationType implementationType() const
Returns the current implementation type that is used to render the lines.
Definition lines.h:379
void setPoints(const std::vector< float > &vertCoords, const std::vector< uint > &lineIndices, const std::vector< float > &vertNormals, const std::vector< uint > &vertColors, const std::vector< uint > &lineColors, ImplementationType type=ImplementationType::COUNT)
Sets the points of the lines.
Definition lines.h:290
ColorToUse colorToUse() const
Returns the color that is used to render the lines.
Definition lines.h:355
void draw(uint viewId) const
Draws in the given view the lines with the current settings.
Definition lines.h:427
ImplementationType defaultImplementationType(bool cpuMemPointsProvided) const
Returns the default supported implementation type that can be used, depending on the capabilities of ...
Definition lines.h:448
Lines(const std::vector< float > &vertCoords, const std::vector< float > &vertNormals, const std::vector< uint > &vertColors, const std::vector< uint > &lineColors, float thickness=5.0f, bool shadingPerVertex=false, ColorToUse colorToUse=ColorToUse::GENERAL, ImplementationType type=ImplementationType::COUNT)
Creates a Lines object with given points and parameters.
Definition lines.h:148
Color & generalColor()
Returns a reference to the general color that is used to render the lines when colorToUse() is set to...
Definition lines.h:371
void setColorToUse(ColorToUse color)
Sets which color to use for rendering the lines.
Definition lines.h:411
Lines(const std::vector< float > &vertCoords, const std::vector< uint > &lineIndices, const std::vector< float > &vertNormals, const std::vector< uint > &vertColors, const std::vector< uint > &lineColors, float thickness=5.0f, bool shadingPerVertex=false, ColorToUse colorToUse=ColorToUse::GENERAL, ImplementationType type=ImplementationType::COUNT)
Creates a Lines object with given points and parameters.
Definition lines.h:195
Lines(ImplementationType type=ImplementationType::COUNT)
Creates a Lines object with default parameters and without points.
Definition lines.h:111
float thickness() const
Returns the thickness of the lines (in pixels).
Definition lines.h:335
float & thickness()
Returns a reference to the thickness of the lines (in pixels). This allows to modify the thickness di...
Definition lines.h:342
bool shadingPerVertex() const
Returns true if shading is computed per vertex using vertex normals, false if no shading is applied.
Definition lines.h:349
Color generalColor() const
Returns the general color that is used to render the lines when colorToUse() is set to ColorToUse::GE...
Definition lines.h:362
void setPoints(const std::vector< float > &vertCoords, const std::vector< float > &vertNormals, const std::vector< uint > &vertColors, const std::vector< uint > &lineColors, ImplementationType type=ImplementationType::COUNT)
Sets the points of the lines.
Definition lines.h:236
void setShading(bool perVertex)
Sets wether to use per vertex shading (using vertex normals) or not.
Definition lines.h:391
The Uniform class wraps a bgfx::UniformHandle and provides a simple interface to set the uniform data...
Definition uniform.h:43
void bind(const void *data) const
Sets the uniform data for the current shader program.
Definition uniform.h:144