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 
6 
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 
19 
20 GeometryResult PointFieldGeometry::GetPositionBuffer(
21  const ContentContext& renderer,
22  const Entity& entity,
23  RenderPass& pass) const {
24  if (radius_ < 0.0) {
25  return {};
26  }
27  const Matrix& transform = entity.GetTransform();
28 
29  Scalar max_basis = transform.GetMaxBasisLengthXY();
30  if (max_basis == 0) {
31  return {};
32  }
33  Scalar min_size = 0.5f / max_basis;
34  Scalar radius = std::max(radius_, min_size);
35 
36  HostBuffer& host_buffer = renderer.GetTransientsBuffer();
37  VertexBufferBuilder<SolidFillVertexShader::PerVertexData> vtx_builder;
38  if (round_) {
39  // Get triangulation relative to {0, 0} so we can translate it to each
40  // point in turn.
41  auto generator =
42  renderer.GetTessellator()->FilledCircle(transform, {}, radius);
43  FML_DCHECK(generator.GetTriangleType() == PrimitiveType::kTriangleStrip);
44  std::vector<Point> circle_vertices;
45  circle_vertices.reserve(generator.GetVertexCount());
46  generator.GenerateVertices([&circle_vertices](const Point& p) { //
47  circle_vertices.push_back(p);
48  });
49  FML_DCHECK(circle_vertices.size() == generator.GetVertexCount());
50 
51  vtx_builder.Reserve((circle_vertices.size() + 2) * points_.size() - 2);
52  for (auto& center : points_) {
53  if (vtx_builder.HasVertices()) {
54  vtx_builder.AppendVertex(vtx_builder.Last());
55  vtx_builder.AppendVertex({center + circle_vertices[0]});
56  }
57 
58  for (auto& vertex : circle_vertices) {
59  vtx_builder.AppendVertex({center + vertex});
60  }
61  }
62  } else {
63  vtx_builder.Reserve(6 * points_.size() - 2);
64  for (auto& point : points_) {
65  auto first = Point(point.x - radius, point.y - radius);
66 
67  if (vtx_builder.HasVertices()) {
68  vtx_builder.AppendVertex(vtx_builder.Last());
69  vtx_builder.AppendVertex({first});
70  }
71 
72  // Z pattern from UL -> UR -> LL -> LR
73  vtx_builder.AppendVertex({first});
74  vtx_builder.AppendVertex({{point.x + radius, point.y - radius}});
75  vtx_builder.AppendVertex({{point.x - radius, point.y + radius}});
76  vtx_builder.AppendVertex({{point.x + radius, point.y + radius}});
77  }
78  }
79 
80  return GeometryResult{
82  .vertex_buffer = vtx_builder.CreateVertexBuffer(host_buffer),
83  .transform = entity.GetShaderTransform(pass),
84  };
85 }
86 
87 // |Geometry|
88 std::optional<Rect> PointFieldGeometry::GetCoverage(
89  const Matrix& transform) const {
90  if (points_.size() > 0) {
91  // Doesn't use MakePointBounds as this isn't resilient to points that
92  // all lie along the same axis.
93  auto first = points_.begin();
94  auto last = points_.end();
95  auto left = first->x;
96  auto top = first->y;
97  auto right = first->x;
98  auto bottom = first->y;
99  for (auto it = first + 1; it < last; ++it) {
100  left = std::min(left, it->x);
101  top = std::min(top, it->y);
102  right = std::max(right, it->x);
103  bottom = std::max(bottom, it->y);
104  }
105  auto coverage = Rect::MakeLTRB(left - radius_, top - radius_,
106  right + radius_, bottom + radius_);
107  return coverage.TransformBounds(transform);
108  }
109  return std::nullopt;
110 }
111 
112 } // namespace impeller
impeller::Entity::GetShaderTransform
Matrix GetShaderTransform(const RenderPass &pass) const
Get the vertex shader transform used for drawing this Entity.
Definition: entity.cc:51
impeller::Scalar
float Scalar
Definition: scalar.h:18
geometry.h
impeller::Entity::GetTransform
const Matrix & GetTransform() const
Get the global transform matrix for this Entity.
Definition: entity.cc:47
point_field_geometry.h
impeller::PointFieldGeometry::PointFieldGeometry
PointFieldGeometry(std::vector< Point > points, Scalar radius, bool round)
Definition: point_field_geometry.cc:13
formats.h
impeller::Entity
Definition: entity.h:20
impeller::PrimitiveType::kTriangleStrip
@ kTriangleStrip
impeller::Point
TPoint< Scalar > Point
Definition: point.h:327
transform
Matrix transform
Definition: gaussian_blur_filter_contents.cc:213
impeller::GeometryResult
Definition: geometry.h:26
impeller::ContentContext::GetTessellator
std::shared_ptr< Tessellator > GetTessellator() const
Definition: content_context.cc:546
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
impeller::PointFieldGeometry::~PointFieldGeometry
~PointFieldGeometry() override
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: allocation.cc:12
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:753