| Flutter Impeller |

point_field_geometry.cc
Go to the documentation of this file.
1 // Copyright 2013 The Flutter Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "impeller/entity/geometry/point_field_geometry.h"
6
7 #include "impeller/core/vertex_buffer.h"
8 #include "impeller/entity/geometry/geometry.h"
9 #include "impeller/renderer/command_buffer.h"
10
11 namespace impeller {
12
13 PointFieldGeometry::PointFieldGeometry(std::vector<Point> points,
14 Scalar radius,
15 bool round)
16 : points_(std::move(points)), radius_(radius), round_(round) {}
17
18 GeometryResult PointFieldGeometry::GetPositionBuffer(
19 const ContentContext& renderer,
20 const Entity& entity,
21 RenderPass& pass) const {
22 if (radius_ < 0.0) {
23 return {};
24 }
25 Matrix transform = entity.GetTransform();
26 Scalar determinant = transform.GetDeterminant();
27 if (determinant == 0) {
28 return {};
29 }
30
31 Scalar min_size = 1.0f / sqrt(std::abs(determinant));
32 Scalar radius = std::max(radius_, min_size);
33
34 HostBuffer& host_buffer = renderer.GetTransientsBuffer();
35 VertexBufferBuilder<SolidFillVertexShader::PerVertexData> vtx_builder;
36
37 if (round_) {
38 // Get triangulation relative to {0, 0} so we can translate it to each
39 // point in turn.
40 auto generator =
41 renderer.GetTessellator()->FilledCircle(transform, {}, radius);
42 FML_DCHECK(generator.GetTriangleType() == PrimitiveType::kTriangleStrip);
43 std::vector<Point> circle_vertices;
44 circle_vertices.reserve(generator.GetVertexCount());
45 generator.GenerateVertices([&circle_vertices](const Point& p) { //
46 circle_vertices.push_back(p);
47 });
48 FML_DCHECK(circle_vertices.size() == generator.GetVertexCount());
49
50 vtx_builder.Reserve((circle_vertices.size() + 2) * points_.size() - 2);
51 for (auto& center : points_) {
52 if (vtx_builder.HasVertices()) {
53 vtx_builder.AppendVertex(vtx_builder.Last());
54 vtx_builder.AppendVertex({center + circle_vertices[0]});
55 }
56
57 for (auto& vertex : circle_vertices) {
58 vtx_builder.AppendVertex({center + vertex});
59 }
60 }
61 } else {
62 vtx_builder.Reserve(6 * points_.size() - 2);
63 for (auto& point : points_) {
64 auto first = Point(point.x - radius, point.y - radius);
65
66 if (vtx_builder.HasVertices()) {
67 vtx_builder.AppendVertex(vtx_builder.Last());
68 vtx_builder.AppendVertex({first});
69 }
70
71 // Z pattern from UL -> UR -> LL -> LR
72 vtx_builder.AppendVertex({first});
73 vtx_builder.AppendVertex({{point.x + radius, point.y - radius}});
74 vtx_builder.AppendVertex({{point.x - radius, point.y + radius}});
75 vtx_builder.AppendVertex({{point.x + radius, point.y + radius}});
76 }
77 }
78
79 return GeometryResult{
80 .type = PrimitiveType::kTriangleStrip,
81 .vertex_buffer = vtx_builder.CreateVertexBuffer(host_buffer),
82 .transform = entity.GetShaderTransform(pass),
83 };
84 }
85
86 // |Geometry|
87 std::optional<Rect> PointFieldGeometry::GetCoverage(
88 const Matrix& transform) const {
89 if (points_.size() > 0) {
90 // Doesn't use MakePointBounds as this isn't resilient to points that
91 // all lie along the same axis.
92 auto first = points_.begin();
93 auto last = points_.end();
94 auto left = first->x;
95 auto top = first->y;
96 auto right = first->x;
97 auto bottom = first->y;
98 for (auto it = first + 1; it < last; ++it) {
99 left = std::min(left, it->x);
100 top = std::min(top, it->y);
101 right = std::max(right, it->x);
102 bottom = std::max(bottom, it->y);
103 }
104 auto coverage = Rect::MakeLTRB(left - radius_, top - radius_,
105 right + radius_, bottom + radius_);
106 return coverage.TransformBounds(transform);
107 }
108 return std::nullopt;
109 }
110
111 } // namespace impeller
impeller::Entity::GetShaderTransform
Matrix GetShaderTransform(const RenderPass &pass) const
Get the vertex shader transform used for drawing this Entity.
Definition: entity.cc:50
impeller::Scalar
float Scalar
Definition: scalar.h:18
impeller::Entity::GetTransform
const Matrix & GetTransform() const
Get the global transform matrix for this Entity.
Definition: entity.cc:46
vertex_buffer.h
point_field_geometry.h
impeller::PointFieldGeometry::PointFieldGeometry
PointFieldGeometry(std::vector< Point > points, Scalar radius, bool round)
Definition: point_field_geometry.cc:13
impeller::Entity
Definition: entity.h:20
impeller::PrimitiveType::kTriangleStrip
@ kTriangleStrip
impeller::Point
TPoint< Scalar > Point
Definition: point.h:322
transform
Matrix transform
Definition: gaussian_blur_filter_contents.cc:231
geometry.h
impeller::GeometryResult
Definition: geometry.h:19
impeller::ContentContext::GetTessellator
std::shared_ptr< Tessellator > GetTessellator() const
Definition: content_context.cc:549
impeller::RenderPass
Render passes encode render commands directed as one specific render target into an underlying comman...
Definition: render_pass.h:33
command_buffer.h
std
Definition: comparable.h:95
impeller::TRect< Scalar >::MakeLTRB
constexpr static TRect MakeLTRB(Type left, Type top, Type right, Type bottom)
Definition: rect.h:129
impeller
Definition: aiks_blend_unittests.cc:18
impeller::ContentContext
Definition: content_context.h:366
impeller::ContentContext::GetTransientsBuffer
HostBuffer & GetTransientsBuffer() const
Retrieve the currnent host buffer for transient storage.
Definition: content_context.h:752