146 {
147 if (draw_data->CmdListsCount == 0) {
148 return;
149 }
150
151 using VS = impeller::ImguiRasterVertexShader;
152 using FS = impeller::ImguiRasterFragmentShader;
153
155 IM_ASSERT(bd != nullptr && "Did you call ImGui_ImplImpeller_Init()?");
156
157 size_t total_vtx_bytes = draw_data->TotalVtxCount * sizeof(VS::PerVertexData);
158 size_t total_idx_bytes = draw_data->TotalIdxCount * sizeof(ImDrawIdx);
159 if (!total_vtx_bytes || !total_idx_bytes) {
160 return;
161 }
162
163
165 buffer_desc.
size = total_vtx_bytes + total_idx_bytes;
167
168 auto buffer = bd->context->GetResourceAllocator()->CreateBuffer(buffer_desc);
169 buffer->SetLabel(
"ImGui vertex+index buffer");
170
172 draw_data->DisplayPos.x, draw_data->DisplayPos.y,
173 draw_data->DisplaySize.x, draw_data->DisplaySize.y);
174
176 .
rect = display_rect.
Scale(draw_data->FramebufferScale.x,
177 draw_data->FramebufferScale.y)};
178
179
180 VS::UniformBuffer uniforms;
184
185 size_t vertex_buffer_offset = 0;
186 size_t index_buffer_offset = total_vtx_bytes;
187
188 for (int draw_list_i = 0; draw_list_i < draw_data->CmdListsCount;
189 draw_list_i++) {
190 const ImDrawList* cmd_list = draw_data->CmdLists[draw_list_i];
191
192
193
194
195
196
197
198
199
200 std::vector<VS::PerVertexData> vtx_data;
201 vtx_data.reserve(cmd_list->VtxBuffer.size());
202 for (const auto& v : cmd_list->VtxBuffer) {
203 ImVec4 color = ImGui::ColorConvertU32ToFloat4(v.col);
204 vtx_data.push_back({{v.pos.x, v.pos.y},
205 {v.uv.x, v.uv.y},
206 {color.x, color.y, color.z, color.w}});
207 }
208
209 auto draw_list_vtx_bytes =
210 static_cast<size_t>(vtx_data.size() * sizeof(VS::PerVertexData));
211 auto draw_list_idx_bytes =
212 static_cast<size_t>(cmd_list->IdxBuffer.size_in_bytes());
213 if (!
buffer->CopyHostBuffer(
reinterpret_cast<uint8_t*
>(vtx_data.data()),
215 vertex_buffer_offset)) {
216 IM_ASSERT(false && "Could not copy vertices to buffer.");
217 }
218 if (!
buffer->CopyHostBuffer(
219 reinterpret_cast<uint8_t*>(cmd_list->IdxBuffer.Data),
221 IM_ASSERT(false && "Could not copy indices to buffer.");
222 }
223
224 for (int cmd_i = 0; cmd_i < cmd_list->CmdBuffer.Size; cmd_i++) {
225 const ImDrawCmd* pcmd = &cmd_list->CmdBuffer[cmd_i];
226
227 if (pcmd->UserCallback) {
228 pcmd->UserCallback(cmd_list, pcmd);
229 } else {
230
232 (pcmd->ClipRect.x - draw_data->DisplayPos.x) *
233 draw_data->FramebufferScale.x,
234 (pcmd->ClipRect.y - draw_data->DisplayPos.y) *
235 draw_data->FramebufferScale.y,
236 (pcmd->ClipRect.z - draw_data->DisplayPos.x) *
237 draw_data->FramebufferScale.x,
238 (pcmd->ClipRect.w - draw_data->DisplayPos.y) *
239 draw_data->FramebufferScale.y);
240 {
241
242 auto visible_clip = clip_rect.Intersection(viewport.rect);
243 if (!visible_clip.has_value()) {
244 continue;
245 }
246 clip_rect = visible_clip.value();
247 }
248 {
249
250
251 auto visible_clip = clip_rect.Intersection(
253 if (!visible_clip.has_value()) {
254 continue;
255 }
256 clip_rect = visible_clip.value();
257 }
258
259 render_pass.SetCommandLabel(
260 std::format("ImGui draw list {} (command {})", draw_list_i, cmd_i));
261 render_pass.SetViewport(viewport);
263 render_pass.SetPipeline(bd->pipeline);
264 VS::BindUniformBuffer(render_pass, vtx_uniforms);
265 FS::BindTex(render_pass, bd->font_texture, bd->sampler);
266
267 size_t vb_start =
268 vertex_buffer_offset + pcmd->VtxOffset * sizeof(ImDrawVert);
269
275 pcmd->IdxOffset * sizeof(ImDrawIdx),
276 pcmd->ElemCount * sizeof(ImDrawIdx)));
279 render_pass.SetVertexBuffer(std::move(vertex_buffer));
280 render_pass.SetBaseVertex(pcmd->VtxOffset);
281
282 render_pass.Draw().ok();
283 }
284 }
285
286 vertex_buffer_offset += draw_list_vtx_bytes;
287 index_buffer_offset += draw_list_idx_bytes;
288 }
290}
BufferView EmplaceUniform(const UniformType &uniform)
Emplace uniform data onto the host buffer. Ensure that backend specific uniform alignment requirement...
void Reset()
Resets the contents of the HostBuffer to nothing so it can be reused.
static ImGui_ImplImpeller_Data * ImGui_ImplImpeller_GetBackendData()
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 to the cache directory This is different from the persistent_cache_path in embedder which is used for Skia shader cache icu native lib Path to the library file that exports the ICU data vm service The hostname IP address on which the Dart VM Service should be served If not defaults to or::depending on whether ipv6 is specified disable vm Disable the Dart VM Service The Dart VM Service is never available in release mode Bind to the IPv6 localhost address for the Dart VM Service Ignored if vm service host is set profile Make the profiler discard new samples once the profiler sample buffer is full When this flag is not the profiler sample buffer is used as a ring buffer
LinePipeline::FragmentShader FS
LinePipeline::VertexShader VS
static constexpr Matrix MakeOrthographic(TSize< T > size)
constexpr Matrix Translate(const Vector3 &t) const
RoundOut(const TRect< U > &r)
static constexpr TRect MakeXYWH(Type x, Type y, Type width, Type height)
constexpr TRect Scale(Type scale) const
static constexpr TRect MakeSize(const TSize< U > &size)
static constexpr TRect MakeLTRB(Type left, Type top, Type right, Type bottom)
BufferView index_buffer
The index buffer binding used by the vertex shader stage.