Flutter Engine
The Flutter Engine
Classes | Public Types | Public Member Functions | Static Public Member Functions | Static Public Attributes | Protected Attributes | List of all members
impeller::Tessellator Class Reference

A utility that generates triangles of the specified fill type given a polyline. This happens on the CPU. More...

#include <tessellator.h>

Classes

class  EllipticalVertexGenerator
 The |VertexGenerator| implementation common to all shapes that are based on a polygonal representation of an ellipse. More...
 
class  VertexGenerator
 An object which produces a list of vertices as |Point|s that tessellate a previously provided shape and delivers the vertices through a |TessellatedVertexProc| callback. More...
 

Public Types

enum class  Result { kSuccess , kInputError , kTessellationError }
 
using TessellatedVertexProc = std::function< void(const Point &p)>
 A callback function for a |VertexGenerator| to deliver the vertices it computes as |Point| objects. More...
 

Public Member Functions

 Tessellator ()
 
virtual ~Tessellator ()
 
VertexBuffer TessellateConvex (const Path &path, HostBuffer &host_buffer, Scalar tolerance)
 Given a convex path, create a triangle fan structure. More...
 
Path::Polyline CreateTempPolyline (const Path &path, Scalar tolerance)
 Create a temporary polyline. Only one per-process can exist at a time. More...
 
EllipticalVertexGenerator FilledCircle (const Matrix &view_transform, const Point &center, Scalar radius)
 Create a |VertexGenerator| that can produce vertices for a filled circle of the given radius around the given center with enough polygon sub-divisions to provide reasonable fidelity when viewed under the given view transform. More...
 
EllipticalVertexGenerator StrokedCircle (const Matrix &view_transform, const Point &center, Scalar radius, Scalar half_width)
 Create a |VertexGenerator| that can produce vertices for a stroked circle of the given radius and half_width around the given shared center with enough polygon sub-divisions to provide reasonable fidelity when viewed under the given view transform. The outer edge of the stroked circle is generated at (radius + half_width) and the inner edge is generated at (radius - half_width). More...
 
EllipticalVertexGenerator RoundCapLine (const Matrix &view_transform, const Point &p0, const Point &p1, Scalar radius)
 Create a |VertexGenerator| that can produce vertices for a line with round end caps of the given radius with enough polygon sub-divisions to provide reasonable fidelity when viewed under the given view transform. More...
 
EllipticalVertexGenerator FilledEllipse (const Matrix &view_transform, const Rect &bounds)
 Create a |VertexGenerator| that can produce vertices for a filled ellipse inscribed within the given bounds with enough polygon sub-divisions to provide reasonable fidelity when viewed under the given view transform. More...
 
EllipticalVertexGenerator FilledRoundRect (const Matrix &view_transform, const Rect &bounds, const Size &radii)
 Create a |VertexGenerator| that can produce vertices for a filled round rect within the given bounds and corner radii with enough polygon sub-divisions to provide reasonable fidelity when viewed under the given view transform. More...
 

Static Public Member Functions

static void TessellateConvexInternal (const Path &path, std::vector< Point > &point_buffer, std::vector< uint16_t > &index_buffer, Scalar tolerance)
 

Static Public Attributes

static constexpr Scalar kCircleTolerance = 0.1f
 The pixel tolerance used by the algorighm to determine how many divisions to create for a circle. More...
 

Protected Attributes

std::unique_ptr< std::vector< Point > > point_buffer_
 Used for polyline generation. More...
 
std::unique_ptr< std::vector< uint16_t > > index_buffer_
 

Detailed Description

A utility that generates triangles of the specified fill type given a polyline. This happens on the CPU.

Also contains functionality for optimized generation of circles and ellipses.

This object is not thread safe, and its methods must not be called from multiple threads.

Definition at line 31 of file tessellator.h.

Member Typedef Documentation

◆ TessellatedVertexProc

A callback function for a |VertexGenerator| to deliver the vertices it computes as |Point| objects.

Definition at line 78 of file tessellator.h.

Member Enumeration Documentation

◆ Result

enum class impeller::Tessellator::Result
strong
Enumerator
kSuccess 
kInputError 
kTessellationError 

Definition at line 70 of file tessellator.h.

70 {
73 kTessellationError,
74 };
@ kSuccess
Definition: embedder.h:73

Constructor & Destructor Documentation

◆ Tessellator()

impeller::Tessellator::Tessellator ( )

Definition at line 9 of file tessellator.cc.

10 : point_buffer_(std::make_unique<std::vector<Point>>()),
11 index_buffer_(std::make_unique<std::vector<uint16_t>>()) {
12 point_buffer_->reserve(2048);
13 index_buffer_->reserve(2048);
14}
std::unique_ptr< std::vector< Point > > point_buffer_
Used for polyline generation.
Definition: tessellator.h:287
std::unique_ptr< std::vector< uint16_t > > index_buffer_
Definition: tessellator.h:288

◆ ~Tessellator()

impeller::Tessellator::~Tessellator ( )
virtualdefault

Member Function Documentation

◆ CreateTempPolyline()

Path::Polyline impeller::Tessellator::CreateTempPolyline ( const Path path,
Scalar  tolerance 
)

Create a temporary polyline. Only one per-process can exist at a time.

The tessellator itself is not a thread safe class and should only be used from the raster thread.

Definition at line 18 of file tessellator.cc.

19 {
21 point_buffer_->clear();
22 auto polyline =
23 path.CreatePolyline(tolerance, std::move(point_buffer_),
24 [this](Path::Polyline::PointBufferPtr point_buffer) {
25 point_buffer_ = std::move(point_buffer);
26 });
27 return polyline;
28}
#define FML_DCHECK(condition)
Definition: logging.h:103
DEF_SWITCHES_START aot vmservice shared library Name of the *so containing AOT compiled Dart assets for launching the service isolate vm snapshot The VM snapshot data that will be memory mapped as read only SnapshotAssetPath must be present isolate snapshot The isolate snapshot data that will be memory mapped as read only SnapshotAssetPath must be present cache dir path
Definition: switches.h:57
const Path::Polyline & polyline
std::unique_ptr< std::vector< Point > > PointBufferPtr
Definition: path.h:98

◆ FilledCircle()

EllipticalVertexGenerator impeller::Tessellator::FilledCircle ( const Matrix view_transform,
const Point center,
Scalar  radius 
)

Create a |VertexGenerator| that can produce vertices for a filled circle of the given radius around the given center with enough polygon sub-divisions to provide reasonable fidelity when viewed under the given view transform.

Note that the view transform is only used to choose the number of sample points to use per quarter circle and the returned points are not transformed by it, instead they are relative to the coordinate space of the center point.

Definition at line 237 of file tessellator.cc.

240 {
241 auto divisions =
242 ComputeQuadrantDivisions(view_transform.GetMaxBasisLength() * radius);
243 return EllipticalVertexGenerator(Tessellator::GenerateFilledCircle,
244 GetTrigsForDivisions(divisions),
246 {
247 .reference_centers = {center, center},
248 .radii = {radius, radius},
249 .half_width = -1.0f,
250 });
251}
static size_t ComputeQuadrantDivisions(Scalar pixel_radius)
Definition: tessellator.cc:144
Tessellator::EllipticalVertexGenerator EllipticalVertexGenerator
Definition: tessellator.cc:224

◆ FilledEllipse()

EllipticalVertexGenerator impeller::Tessellator::FilledEllipse ( const Matrix view_transform,
const Rect bounds 
)

Create a |VertexGenerator| that can produce vertices for a filled ellipse inscribed within the given bounds with enough polygon sub-divisions to provide reasonable fidelity when viewed under the given view transform.

Note that the view transform is only used to choose the number of sample points to use per quarter circle and the returned points are not transformed by it, instead they are relative to the coordinate space of the bounds.

Definition at line 297 of file tessellator.cc.

299 {
300 if (bounds.IsSquare()) {
301 return FilledCircle(view_transform, bounds.GetCenter(),
302 bounds.GetWidth() * 0.5f);
303 }
304 auto max_radius = bounds.GetSize().MaxDimension();
305 auto divisions =
306 ComputeQuadrantDivisions(view_transform.GetMaxBasisLength() * max_radius);
307 auto center = bounds.GetCenter();
308 return EllipticalVertexGenerator(Tessellator::GenerateFilledEllipse,
309 GetTrigsForDivisions(divisions),
311 {
312 .reference_centers = {center, center},
313 .radii = bounds.GetSize() * 0.5f,
314 .half_width = -1.0f,
315 });
316}
EllipticalVertexGenerator FilledCircle(const Matrix &view_transform, const Point &center, Scalar radius)
Create a |VertexGenerator| that can produce vertices for a filled circle of the given radius around t...
Definition: tessellator.cc:237
Optional< SkRect > bounds
Definition: SkRecords.h:189

◆ FilledRoundRect()

EllipticalVertexGenerator impeller::Tessellator::FilledRoundRect ( const Matrix view_transform,
const Rect bounds,
const Size radii 
)

Create a |VertexGenerator| that can produce vertices for a filled round rect within the given bounds and corner radii with enough polygon sub-divisions to provide reasonable fidelity when viewed under the given view transform.

Note that the view transform is only used to choose the number of sample points to use per quarter circle and the returned points are not transformed by it, instead they are relative to the coordinate space of the bounds.

Definition at line 318 of file tessellator.cc.

321 {
322 if (radii.width * 2 < bounds.GetWidth() ||
323 radii.height * 2 < bounds.GetHeight()) {
324 auto max_radius = radii.MaxDimension();
325 auto divisions = ComputeQuadrantDivisions(
326 view_transform.GetMaxBasisLength() * max_radius);
327 auto upper_left = bounds.GetLeftTop() + radii;
328 auto lower_right = bounds.GetRightBottom() - radii;
329 return EllipticalVertexGenerator(Tessellator::GenerateFilledRoundRect,
330 GetTrigsForDivisions(divisions),
332 {
333 .reference_centers =
334 {
335 upper_left,
336 lower_right,
337 },
338 .radii = radii,
339 .half_width = -1.0f,
340 });
341 } else {
342 return FilledEllipse(view_transform, bounds);
343 }
344}
EllipticalVertexGenerator FilledEllipse(const Matrix &view_transform, const Rect &bounds)
Create a |VertexGenerator| that can produce vertices for a filled ellipse inscribed within the given ...
Definition: tessellator.cc:297

◆ RoundCapLine()

EllipticalVertexGenerator impeller::Tessellator::RoundCapLine ( const Matrix view_transform,
const Point p0,
const Point p1,
Scalar  radius 
)

Create a |VertexGenerator| that can produce vertices for a line with round end caps of the given radius with enough polygon sub-divisions to provide reasonable fidelity when viewed under the given view transform.

Note that the view transform is only used to choose the number of sample points to use per quarter circle and the returned points are not transformed by it, instead they are relative to the coordinate space of the two points.

Definition at line 274 of file tessellator.cc.

278 {
279 auto along = p1 - p0;
280 auto length = along.GetLength();
281 if (length > kEhCloseEnough) {
282 auto divisions =
283 ComputeQuadrantDivisions(view_transform.GetMaxBasisLength() * radius);
284 return EllipticalVertexGenerator(Tessellator::GenerateRoundCapLine,
285 GetTrigsForDivisions(divisions),
287 {
288 .reference_centers = {p0, p1},
289 .radii = {radius, radius},
290 .half_width = -1.0f,
291 });
292 } else {
293 return FilledCircle(view_transform, p0, radius);
294 }
295}
size_t length
constexpr float kEhCloseEnough
Definition: constants.h:56

◆ StrokedCircle()

EllipticalVertexGenerator impeller::Tessellator::StrokedCircle ( const Matrix view_transform,
const Point center,
Scalar  radius,
Scalar  half_width 
)

Create a |VertexGenerator| that can produce vertices for a stroked circle of the given radius and half_width around the given shared center with enough polygon sub-divisions to provide reasonable fidelity when viewed under the given view transform. The outer edge of the stroked circle is generated at (radius + half_width) and the inner edge is generated at (radius - half_width).

Note that the view transform is only used to choose the number of sample points to use per quarter circle and the returned points are not transformed by it, instead they are relative to the coordinate space of the center point.

Definition at line 253 of file tessellator.cc.

257 {
258 if (half_width > 0) {
259 auto divisions = ComputeQuadrantDivisions(
260 view_transform.GetMaxBasisLength() * radius + half_width);
261 return EllipticalVertexGenerator(Tessellator::GenerateStrokedCircle,
262 GetTrigsForDivisions(divisions),
264 {
265 .reference_centers = {center, center},
266 .radii = {radius, radius},
267 .half_width = half_width,
268 });
269 } else {
270 return FilledCircle(view_transform, center, radius);
271 }
272}

◆ TessellateConvex()

VertexBuffer impeller::Tessellator::TessellateConvex ( const Path path,
HostBuffer host_buffer,
Scalar  tolerance 
)

Given a convex path, create a triangle fan structure.

Parameters
[in]pathThe path to tessellate.
[in]toleranceThe tolerance value for conversion of the path to a polyline. This value is often derived from the Matrix::GetMaxBasisLength of the CTM applied to the path for rendering.
Returns
A point vector containing the vertices in triangle strip format.
Parameters
[in]host_bufferThe host buffer for allocation of vertices/index data.
Returns
A vertex buffer containing all data from the provided curve.

Definition at line 30 of file tessellator.cc.

32 {
36
37 if (point_buffer_->empty()) {
38 return VertexBuffer{
39 .vertex_buffer = {},
40 .index_buffer = {},
41 .vertex_count = 0u,
42 .index_type = IndexType::k16bit,
43 };
44 }
45
46 BufferView vertex_buffer = host_buffer.Emplace(
47 point_buffer_->data(), sizeof(Point) * point_buffer_->size(),
48 alignof(Point));
49
50 BufferView index_buffer = host_buffer.Emplace(
51 index_buffer_->data(), sizeof(uint16_t) * index_buffer_->size(),
52 alignof(uint16_t));
53
54 return VertexBuffer{
55 .vertex_buffer = std::move(vertex_buffer),
56 .index_buffer = std::move(index_buffer),
57 .vertex_count = index_buffer_->size(),
58 .index_type = IndexType::k16bit,
59 };
60}
static void TessellateConvexInternal(const Path &path, std::vector< Point > &point_buffer, std::vector< uint16_t > &index_buffer, Scalar tolerance)
Definition: tessellator.cc:62
TPoint< Scalar > Point
Definition: point.h:322

◆ TessellateConvexInternal()

void impeller::Tessellator::TessellateConvexInternal ( const Path path,
std::vector< Point > &  point_buffer,
std::vector< uint16_t > &  index_buffer,
Scalar  tolerance 
)
static

Visible for testing.

This method only exists for the ease of benchmarking without using the real allocator needed by the [host_buffer].

Definition at line 62 of file tessellator.cc.

65 {
66 point_buffer.clear();
67 index_buffer.clear();
68
69 VertexWriter writer(point_buffer, index_buffer);
70
71 path.WritePolyline(tolerance, writer);
72}

Member Data Documentation

◆ index_buffer_

std::unique_ptr<std::vector<uint16_t> > impeller::Tessellator::index_buffer_
protected

Definition at line 288 of file tessellator.h.

◆ kCircleTolerance

constexpr Scalar impeller::Tessellator::kCircleTolerance = 0.1f
staticconstexpr

The pixel tolerance used by the algorighm to determine how many divisions to create for a circle.

No point on the polygon of vertices should deviate from the true circle by more than this tolerance.

Definition at line 214 of file tessellator.h.

◆ point_buffer_

std::unique_ptr<std::vector<Point> > impeller::Tessellator::point_buffer_
protected

Used for polyline generation.

Definition at line 287 of file tessellator.h.


The documentation for this class was generated from the following files: