roo_display
API Documentation for roo_display
Loading...
Searching...
No Matches
streamable_stack.h
Go to the documentation of this file.
1#pragma once
2
3#include <vector>
4
8
9namespace roo_display {
10
11/// Multi-layer stack of streamables composited in order.
13 public:
14 /// An input layer in the stack.
15 class Input {
16 public:
17 /// Create an input layer using the source extents.
19 : obj_(obj),
20 extents_(extents),
21 dx_(0),
22 dy_(0),
23 blending_mode_(BlendingMode::kSourceOver) {}
24
25 /// Create an input layer with an offset.
27 : obj_(obj),
28 extents_(extents.translate(dx, dy)),
29 dx_(dx),
30 dy_(dy),
31 blending_mode_(BlendingMode::kSourceOver) {}
32
33 /// Return extents in stack coordinates.
34 const Box& extents() const { return extents_; }
35
36 /// X offset applied to the input.
37 int16_t dx() const { return dx_; }
38 /// Y offset applied to the input.
39 int16_t dy() const { return dy_; }
40
41 /// Create a stream for the given extents in stack coordinates.
42 std::unique_ptr<PixelStream> createStream(const Box& extents) const {
43 return obj_->createStream(extents.translate(-dx_, -dy_));
44 }
45
46 /// Set blending mode for this input.
48 blending_mode_ = mode;
49 return *this;
50 }
51
52 /// Return blending mode for this input.
53 BlendingMode blending_mode() const { return blending_mode_; }
54
55 private:
56 const Streamable* obj_;
57 Box extents_; // After translation, i.e. in the stack coordinates.
58 int16_t dx_;
59 int16_t dy_;
60 BlendingMode blending_mode_;
61 };
62
63 /// Create a stack with the given extents.
65 : extents_(extents), anchor_extents_(extents) {}
66
67 /// Add an input using its full extents.
69 inputs_.emplace_back(input, input->extents());
70 return inputs_.back();
71 }
72
73 /// Add an input clipped to `clip_box`.
74 Input& addInput(const Streamable* input, Box clip_box) {
75 inputs_.emplace_back(input, Box::Intersect(input->extents(), clip_box));
76 return inputs_.back();
77 }
78
79 /// Add an input with an offset.
81 inputs_.emplace_back(input, input->extents(), dx, dy);
82 return inputs_.back();
83 }
84
85 /// Add an input with an offset and clip box.
86 Input& addInput(const Streamable* input, Box clip_box, uint16_t dx,
87 uint16_t dy) {
88 inputs_.emplace_back(input, Box::Intersect(input->extents(), clip_box), dx,
89 dy);
90 return inputs_.back();
91 }
92
93 /// Return the overall extents of the stack.
94 Box extents() const override { return extents_; }
95
96 Box anchorExtents() const override { return anchor_extents_; }
97
98 /// Return minimal extents that fit all inputs without clipping.
100 if (inputs_.empty()) return Box(0, 0, -1, -1);
101 Box result = inputs_[0].extents();
102 for (size_t i = 1; i < inputs_.size(); i++) {
103 result = Box::Extent(result, inputs_[i].extents());
104 }
105 return result;
106 }
107
108 /// Create a stream for the full stack.
109 std::unique_ptr<PixelStream> createStream() const override;
110
111 /// Create a stream for a clipped box.
112 std::unique_ptr<PixelStream> createStream(const Box& clip_box) const override;
113
114 /// Set the stack extents.
115 void setExtents(const Box& extents) { extents_ = extents; }
116
117 /// Set anchor extents used for alignment.
119 anchor_extents_ = anchor_extents;
120 }
121
122 private:
123 void drawTo(const Surface& s) const override;
124
125 Box extents_;
126 Box anchor_extents_;
127 std::vector<Input> inputs_;
128};
129
130} // namespace roo_display
Axis-aligned integer rectangle.
Definition box.h:12
Box translate(int16_t x_offset, int16_t y_offset) const
Return a translated copy of this box.
Definition box.h:127
static Box Extent(const Box &a, const Box &b)
Return the smallest box that contains both input boxes.
Definition box.h:34
static Box Intersect(const Box &a, const Box &b)
Return the intersection of two boxes (may be empty).
Definition box.h:25
An input layer in the stack.
BlendingMode blending_mode() const
Return blending mode for this input.
const Box & extents() const
Return extents in stack coordinates.
std::unique_ptr< PixelStream > createStream(const Box &extents) const
Create a stream for the given extents in stack coordinates.
Input(const Streamable *obj, Box extents)
Create an input layer using the source extents.
int16_t dy() const
Y offset applied to the input.
Input(const Streamable *obj, Box extents, uint16_t dx, uint16_t dy)
Create an input layer with an offset.
int16_t dx() const
X offset applied to the input.
Input & withMode(BlendingMode mode)
Set blending mode for this input.
Multi-layer stack of streamables composited in order.
Input & addInput(const Streamable *input)
Add an input using its full extents.
void setAnchorExtents(const Box &anchor_extents)
Set anchor extents used for alignment.
Box anchorExtents() const override
Return the bounds used for alignment.
Input & addInput(const Streamable *input, uint16_t dx, uint16_t dy)
Add an input with an offset.
Box extents() const override
Return the overall extents of the stack.
Input & addInput(const Streamable *input, Box clip_box, uint16_t dx, uint16_t dy)
Add an input with an offset and clip box.
std::unique_ptr< PixelStream > createStream() const override
Create a stream for the full stack.
void setExtents(const Box &extents)
Set the stack extents.
Input & addInput(const Streamable *input, Box clip_box)
Add an input clipped to clip_box.
Box naturalExtents()
Return minimal extents that fit all inputs without clipping.
StreamableStack(const Box &extents)
Create a stack with the given extents.
Drawable that can provide a sequential pixel stream.
Definition streamable.h:426
virtual std::unique_ptr< PixelStream > createStream() const =0
Create a stream covering the full extents().
Low-level handle used to draw to an underlying device.
Definition drawable.h:60
Defines 140 opaque HTML named colors.
BlendingMode
Porter-Duff style blending modes.
Definition blending.h:17
@ kSourceOver
Source is placed (alpha-blended) over the destination. This is the default blending mode.