Skip to content
This repository was archived by the owner on Feb 25, 2025. It is now read-only.

Commit c64dffe

Browse files
authored
[Flutter GPU] Use vm.Vector4 for clear color instead of ui.Color. (#55416)
Resolves flutter/flutter#155627. Allow setting the clear directly as floats without conversion work. vector_math already has convenient `Colors.[color]` factories and such. Also, `ui.Color` has a color space now, which does not apply here. Adds a simple golden to verify that clear colors work: ![flutter_gpu_test_clear_color](https://github.com/user-attachments/assets/ba7a4e74-aaf2-48d8-ac13-115a86daeb19)
1 parent 16bdf23 commit c64dffe

File tree

6 files changed

+50
-27
lines changed

6 files changed

+50
-27
lines changed

lib/gpu/lib/gpu.dart

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,8 @@ import 'dart:typed_data';
2626
// ignore: uri_does_not_exist
2727
import 'dart:ui' as ui;
2828

29+
import 'package:vector_math/vector_math.dart' as vm;
30+
2931
part 'src/buffer.dart';
3032
part 'src/command_buffer.dart';
3133
part 'src/context.dart';

lib/gpu/lib/src/render_pass.dart

Lines changed: 21 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -10,14 +10,14 @@ base class ColorAttachment {
1010
ColorAttachment({
1111
this.loadAction = LoadAction.clear,
1212
this.storeAction = StoreAction.store,
13-
this.clearValue = const ui.Color(0x00000000),
13+
vm.Vector4? clearValue = null,
1414
required this.texture,
1515
this.resolveTexture = null,
16-
});
16+
}) : clearValue = clearValue ?? vm.Vector4.zero();
1717

1818
LoadAction loadAction;
1919
StoreAction storeAction;
20-
ui.Color clearValue;
20+
vm.Vector4 clearValue;
2121

2222
Texture texture;
2323
Texture? resolveTexture;
@@ -121,15 +121,6 @@ base class RenderTarget {
121121
final DepthStencilAttachment? depthStencilAttachment;
122122
}
123123

124-
// TODO(gaaclarke): Refactor this to support wide gamut colors.
125-
int _colorToInt(ui.Color color) {
126-
assert(color.colorSpace == ui.ColorSpace.sRGB);
127-
return ((color.a * 255.0).round() << 24) |
128-
((color.r * 255.0).round() << 16) |
129-
((color.g * 255.0).round() << 8) |
130-
((color.b * 255.0).round() << 0);
131-
}
132-
133124
base class RenderPass extends NativeFieldWrapperClass1 {
134125
/// Creates a new RenderPass.
135126
RenderPass._(CommandBuffer commandBuffer, RenderTarget renderTarget) {
@@ -140,7 +131,10 @@ base class RenderPass extends NativeFieldWrapperClass1 {
140131
index,
141132
color.loadAction.index,
142133
color.storeAction.index,
143-
_colorToInt(color.clearValue),
134+
color.clearValue.r,
135+
color.clearValue.g,
136+
color.clearValue.b,
137+
color.clearValue.a,
144138
color.texture,
145139
color.resolveTexture);
146140
if (error != null) {
@@ -280,13 +274,25 @@ base class RenderPass extends NativeFieldWrapperClass1 {
280274
external void _initialize();
281275

282276
@Native<
283-
Handle Function(Pointer<Void>, Int, Int, Int, Int, Pointer<Void>,
277+
Handle Function(
278+
Pointer<Void>,
279+
Int,
280+
Int,
281+
Int,
282+
Float,
283+
Float,
284+
Float,
285+
Float,
286+
Pointer<Void>,
284287
Handle)>(symbol: 'InternalFlutterGpu_RenderPass_SetColorAttachment')
285288
external String? _setColorAttachment(
286289
int colorAttachmentIndex,
287290
int loadAction,
288291
int storeAction,
289-
int clearColor,
292+
double clearColorR,
293+
double clearColorG,
294+
double clearColorB,
295+
double clearColorA,
290296
Texture texture,
291297
Texture? resolveTexture);
292298

lib/gpu/pubspec.yaml

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,5 +11,10 @@ environment:
1111
sdk: '>=3.2.0-0 <4.0.0'
1212

1313
dependencies:
14+
# To update these, use "flutter update-packages --force-upgrade".
15+
#
16+
# For detailed instructions, refer to:
17+
# https://github.com/flutter/flutter/blob/main/docs/infra/Updating-dependencies-in-Flutter.md
18+
vector_math: ^2.1.4
1419
sky_engine:
1520
sdk: flutter

lib/gpu/render_pass.cc

Lines changed: 6 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -194,13 +194,6 @@ bool RenderPass::Draw() {
194194
} // namespace gpu
195195
} // namespace flutter
196196

197-
static impeller::Color ToImpellerColor(uint32_t argb) {
198-
return impeller::Color::MakeRGBA8((argb >> 16) & 0xFF, // R
199-
(argb >> 8) & 0xFF, // G
200-
argb & 0xFF, // B
201-
argb >> 24); // A
202-
}
203-
204197
//----------------------------------------------------------------------------
205198
/// Exports
206199
///
@@ -215,13 +208,17 @@ Dart_Handle InternalFlutterGpu_RenderPass_SetColorAttachment(
215208
int color_attachment_index,
216209
int load_action,
217210
int store_action,
218-
int clear_color,
211+
float clear_color_r,
212+
float clear_color_g,
213+
float clear_color_b,
214+
float clear_color_a,
219215
flutter::gpu::Texture* texture,
220216
Dart_Handle resolve_texture_wrapper) {
221217
impeller::ColorAttachment desc;
222218
desc.load_action = flutter::gpu::ToImpellerLoadAction(load_action);
223219
desc.store_action = flutter::gpu::ToImpellerStoreAction(store_action);
224-
desc.clear_color = ToImpellerColor(static_cast<uint32_t>(clear_color));
220+
desc.clear_color = impeller::Color(clear_color_r, clear_color_g,
221+
clear_color_b, clear_color_a);
225222
desc.texture = texture->GetTexture();
226223
if (!Dart_IsNull(resolve_texture_wrapper)) {
227224
flutter::gpu::Texture* resolve_texture =

lib/gpu/render_pass.h

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -107,7 +107,10 @@ extern Dart_Handle InternalFlutterGpu_RenderPass_SetColorAttachment(
107107
int color_attachment_index,
108108
int load_action,
109109
int store_action,
110-
int clear_color,
110+
float clear_color_r,
111+
float clear_color_g,
112+
float clear_color_b,
113+
float clear_color_a,
111114
flutter::gpu::Texture* texture,
112115
Dart_Handle resolve_texture_wrapper);
113116

testing/dart/gpu_test.dart

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,7 @@ class RenderPassState {
5252
}
5353

5454
/// Create a simple RenderPass with simple color and depth-stencil attachments.
55-
RenderPassState createSimpleRenderPass() {
55+
RenderPassState createSimpleRenderPass({Vector4? clearColor}) {
5656
final gpu.Texture? renderTexture =
5757
gpu.gpuContext.createTexture(gpu.StorageMode.devicePrivate, 100, 100);
5858
assert(renderTexture != null);
@@ -64,7 +64,7 @@ RenderPassState createSimpleRenderPass() {
6464
final gpu.CommandBuffer commandBuffer = gpu.gpuContext.createCommandBuffer();
6565

6666
final gpu.RenderTarget renderTarget = gpu.RenderTarget.singleColor(
67-
gpu.ColorAttachment(texture: renderTexture!),
67+
gpu.ColorAttachment(texture: renderTexture!, clearValue: clearColor),
6868
depthStencilAttachment:
6969
gpu.DepthStencilAttachment(texture: depthStencilTexture!));
7070

@@ -324,6 +324,16 @@ void main() async {
324324
}
325325
}, skip: !impellerEnabled);
326326

327+
// Performs no draw calls. Just clears the render target to a solid green color.
328+
test('Can render clear color', () async {
329+
final state = createSimpleRenderPass(clearColor: Colors.lime);
330+
331+
state.commandBuffer.submit();
332+
333+
final ui.Image image = state.renderTexture.asImage();
334+
await comparer.addGoldenImage(image, 'flutter_gpu_test_clear_color.png');
335+
}, skip: !impellerEnabled);
336+
327337
// Renders a green triangle pointing downwards.
328338
test('Can render triangle', () async {
329339
final state = createSimpleRenderPass();

0 commit comments

Comments
 (0)