Skip to content

Commit a781e2f

Browse files
bderodnfield
authored andcommitted
Setup join/cap proc (flutter#45)
1 parent c11f408 commit a781e2f

File tree

3 files changed

+86
-39
lines changed

3 files changed

+86
-39
lines changed

impeller/entity/contents.cc

Lines changed: 59 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -282,7 +282,11 @@ const IRect& TextureContents::GetSourceRect() const {
282282
******* SolidStrokeContents
283283
******************************************************************************/
284284

285-
SolidStrokeContents::SolidStrokeContents() = default;
285+
SolidStrokeContents::SolidStrokeContents() {
286+
SetStrokeCap(Cap::kButt);
287+
// TODO(99089): Change this to kMiter once implemented.
288+
SetStrokeJoin(Join::kBevel);
289+
}
286290

287291
SolidStrokeContents::~SolidStrokeContents() = default;
288292

@@ -294,32 +298,11 @@ const Color& SolidStrokeContents::GetColor() const {
294298
return color_;
295299
}
296300

297-
static void CreateCap(
298-
VertexBufferBuilder<SolidStrokeVertexShader::PerVertexData>& vtx_builder,
299-
const Point& position,
300-
const Point& normal) {}
301-
302-
static void CreateJoin(
303-
VertexBufferBuilder<SolidStrokeVertexShader::PerVertexData>& vtx_builder,
304-
const Point& position,
305-
const Point& start_normal,
306-
const Point& end_normal) {
307-
SolidStrokeVertexShader::PerVertexData vtx;
308-
vtx.vertex_position = position;
309-
vtx.pen_down = 1.0;
310-
vtx.vertex_normal = {};
311-
vtx_builder.AppendVertex(vtx);
312-
313-
// A simple bevel join to start with.
314-
Scalar dir = start_normal.Cross(end_normal) > 0 ? -1 : 1;
315-
vtx.vertex_normal = start_normal * dir;
316-
vtx_builder.AppendVertex(vtx);
317-
vtx.vertex_normal = end_normal * dir;
318-
vtx_builder.AppendVertex(vtx);
319-
}
320-
321-
static VertexBuffer CreateSolidStrokeVertices(const Path& path,
322-
HostBuffer& buffer) {
301+
static VertexBuffer CreateSolidStrokeVertices(
302+
const Path& path,
303+
HostBuffer& buffer,
304+
const SolidStrokeContents::CapProc& cap_proc,
305+
const SolidStrokeContents::JoinProc& join_proc) {
323306
using VS = SolidStrokeVertexShader;
324307

325308
VertexBufferBuilder<VS::PerVertexData> vtx_builder;
@@ -372,7 +355,7 @@ static VertexBuffer CreateSolidStrokeVertices(const Path& path,
372355

373356
// Generate start cap.
374357
if (!polyline.contours[contour_i].is_closed) {
375-
CreateCap(vtx_builder, polyline.points[contour_start_point_i], -normal);
358+
cap_proc(vtx_builder, polyline.points[contour_start_point_i], -normal);
376359
}
377360

378361
// Generate contour geometry.
@@ -396,18 +379,18 @@ static VertexBuffer CreateSolidStrokeVertices(const Path& path,
396379
compute_normal(point_i + 1);
397380

398381
// Generate join from the current line to the next line.
399-
CreateJoin(vtx_builder, polyline.points[point_i], previous_normal,
400-
normal);
382+
join_proc(vtx_builder, polyline.points[point_i], previous_normal,
383+
normal);
401384
}
402385
}
403386
}
404387

405388
// Generate end cap or join.
406389
if (!polyline.contours[contour_i].is_closed) {
407-
CreateCap(vtx_builder, polyline.points[contour_end_point_i - 1], normal);
390+
cap_proc(vtx_builder, polyline.points[contour_end_point_i - 1], normal);
408391
} else {
409-
CreateJoin(vtx_builder, polyline.points[contour_start_point_i], normal,
410-
contour_first_normal);
392+
join_proc(vtx_builder, polyline.points[contour_start_point_i], normal,
393+
contour_first_normal);
411394
}
412395
}
413396

@@ -436,8 +419,8 @@ bool SolidStrokeContents::Render(const ContentContext& renderer,
436419
cmd.label = "SolidStroke";
437420
cmd.pipeline = renderer.GetSolidStrokePipeline(OptionsFromPass(pass));
438421
cmd.stencil_reference = entity.GetStencilDepth();
439-
cmd.BindVertices(
440-
CreateSolidStrokeVertices(entity.GetPath(), pass.GetTransientsBuffer()));
422+
cmd.BindVertices(CreateSolidStrokeVertices(
423+
entity.GetPath(), pass.GetTransientsBuffer(), cap_proc_, join_proc_));
441424
VS::BindFrameInfo(cmd, pass.GetTransientsBuffer().EmplaceUniform(frame_info));
442425
VS::BindStrokeInfo(cmd,
443426
pass.GetTransientsBuffer().EmplaceUniform(stroke_info));
@@ -465,6 +448,20 @@ Scalar SolidStrokeContents::GetStrokeMiter(Scalar miter) {
465448

466449
void SolidStrokeContents::SetStrokeCap(Cap cap) {
467450
cap_ = cap;
451+
452+
using VS = SolidStrokeVertexShader;
453+
switch (cap) {
454+
case Cap::kButt:
455+
cap_proc_ = [](VertexBufferBuilder<VS::PerVertexData>& vtx_builder,
456+
const Point& position, const Point& normal) {};
457+
break;
458+
case Cap::kRound:
459+
FML_DLOG(ERROR) << "Unimplemented.";
460+
break;
461+
case Cap::kSquare:
462+
FML_DLOG(ERROR) << "Unimplemented.";
463+
break;
464+
}
468465
}
469466

470467
SolidStrokeContents::Cap SolidStrokeContents::GetStrokeCap() {
@@ -473,6 +470,33 @@ SolidStrokeContents::Cap SolidStrokeContents::GetStrokeCap() {
473470

474471
void SolidStrokeContents::SetStrokeJoin(Join join) {
475472
join_ = join;
473+
474+
using VS = SolidStrokeVertexShader;
475+
switch (join) {
476+
case Join::kBevel:
477+
join_proc_ = [](VertexBufferBuilder<VS::PerVertexData>& vtx_builder,
478+
const Point& position, const Point& start_normal,
479+
const Point& end_normal) {
480+
SolidStrokeVertexShader::PerVertexData vtx;
481+
vtx.vertex_position = position;
482+
vtx.pen_down = 1.0;
483+
vtx.vertex_normal = {};
484+
vtx_builder.AppendVertex(vtx);
485+
486+
Scalar dir = start_normal.Cross(end_normal) > 0 ? -1 : 1;
487+
vtx.vertex_normal = start_normal * dir;
488+
vtx_builder.AppendVertex(vtx);
489+
vtx.vertex_normal = end_normal * dir;
490+
vtx_builder.AppendVertex(vtx);
491+
};
492+
break;
493+
case Join::kMiter:
494+
FML_DLOG(ERROR) << "Unimplemented.";
495+
break;
496+
case Join::kRound:
497+
FML_DLOG(ERROR) << "Unimplemented.";
498+
break;
499+
}
476500
}
477501

478502
SolidStrokeContents::Join SolidStrokeContents::GetStrokeJoin() {

impeller/entity/contents.h

Lines changed: 18 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -4,10 +4,12 @@
44

55
#pragma once
66

7+
#include <functional>
78
#include <memory>
89
#include <vector>
910

1011
#include "flutter/fml/macros.h"
12+
#include "impeller/entity/solid_stroke.vert.h"
1113
#include "impeller/geometry/color.h"
1214
#include "impeller/geometry/point.h"
1315
#include "impeller/geometry/rect.h"
@@ -119,16 +121,24 @@ class SolidStrokeContents final : public Contents {
119121
kButt,
120122
kRound,
121123
kSquare,
122-
kLast,
123124
};
124125

125126
enum class Join {
126127
kMiter,
127128
kRound,
128129
kBevel,
129-
kLast,
130130
};
131131

132+
using CapProc = std::function<void(
133+
VertexBufferBuilder<SolidStrokeVertexShader::PerVertexData>& vtx_builder,
134+
const Point& position,
135+
const Point& normal)>;
136+
using JoinProc = std::function<void(
137+
VertexBufferBuilder<SolidStrokeVertexShader::PerVertexData>& vtx_builder,
138+
const Point& position,
139+
const Point& start_normal,
140+
const Point& end_normal)>;
141+
132142
SolidStrokeContents();
133143

134144
~SolidStrokeContents() override;
@@ -162,8 +172,12 @@ class SolidStrokeContents final : public Contents {
162172
Color color_;
163173
Scalar stroke_size_ = 0.0;
164174
Scalar miter_ = 0.0;
165-
Cap cap_ = Cap::kButt;
166-
Join join_ = Join::kMiter;
175+
176+
Cap cap_;
177+
CapProc cap_proc_;
178+
179+
Join join_;
180+
JoinProc join_proc_;
167181

168182
FML_DISALLOW_COPY_AND_ASSIGN(SolidStrokeContents);
169183
};

impeller/entity/entity_unittests.cc

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
// Use of this source code is governed by a BSD-style license that can be
33
// found in the LICENSE file.
44

5+
#include "entity/contents.h"
56
#include "flutter/testing/testing.h"
67
#include "impeller/entity/entity.h"
78
#include "impeller/entity/entity_playground.h"
@@ -328,5 +329,13 @@ TEST_F(EntityTest, CubicCurveAndOverlapTest) {
328329
ASSERT_TRUE(OpenPlaygroundHere(entity));
329330
}
330331

332+
TEST_F(EntityTest, SolidStrokeContentsSetStrokeDefaults) {
333+
SolidStrokeContents stroke;
334+
ASSERT_EQ(stroke.GetStrokeCap(), SolidStrokeContents::Cap::kButt);
335+
ASSERT_EQ(stroke.GetStrokeJoin(), SolidStrokeContents::Join::kBevel);
336+
// TODO(99089): Test that SetStroke[Cap|Join] works once there are multiple
337+
// caps and joins.
338+
}
339+
331340
} // namespace testing
332341
} // namespace impeller

0 commit comments

Comments
 (0)