flutter3d
Showcase Changelog 38 packages API reference

Procedural textures: the source

since 0.5.0 Scene and geometry

Regions the guide quotes: encode (line 35), upload (line 42), scene (line 56), check (line 93).

1/// Two textures encoded in Dart and uploaded through the active device.
2library;
3
4import 'dart:typed_data';
5
6import 'package:flutter3d/flutter3d.dart';
7import 'package:flutter3d_showcase/src/demo/demo.dart';
8import 'package:vector_math/vector_math.dart';
9
10final class ProceduralTexturesDemo extends ShowcaseDemo {
11 final SolidColorTexture _solid = SolidColorTexture(
12 Vector4(0.12, 0.55, 0.92, 1.0),
13 );
14 static const CheckerboardTexture _checker = CheckerboardTexture(
15 size: 64,
16 cell: 8,
17 light: 0xF0C86A,
18 dark: 0x314A72,
19 );
21 late final Material _solidMaterial;
22 late final Material _checkerMaterial;
24 @override
25 void configureView(DemoContext context) {
26 context.orbit
27 ..distance = 7.5
28 ..pitch = 0.24
29 ..yaw = 0.35;
30 context.orbit.target.setValues(0.0, 0.8, 0.0);
31 }
33 @override
34 Scene build(DemoContext context) {
35 final ByteData solidPixels = _solid.encode();
36 final ByteData checkerPixels = _checker.encode();
37 if (solidPixels.lengthInBytes != 4 ||
38 checkerPixels.lengthInBytes != 64 * 64 * 4) {
39 throw StateError('a procedural texture returned the wrong byte count');
40 }
42 _solidMaterial = Material(
43 name: 'solid blue',
44 baseColor: Vector4(1.0, 1.0, 1.0, 1.0),
45 albedo: _solid.upload(context.device),
46 roughness: 0.42,
47 );
48 _checkerMaterial = Material(
49 name: 'checkerboard',
50 baseColor: Vector4(1.0, 1.0, 1.0, 1.0),
51 albedo: _checker.upload(context.device),
52 albedoSampler: SamplerOptions.linearRepeat,
53 roughness: 0.58,
54 );
56 final Scene scene = Scene()
57 ..ambientColor = Vector3(0.45, 0.54, 0.72)
58 ..ambientIntensity = 0.14
59 ..add(
60 MeshNode(
61 DeviceMesh.upload(
62 context.device,
63 const SphereShape(radius: 1.05, segments: 36, rings: 18).build(),
64 ),
65 _solidMaterial,
66 name: 'solid sphere',
67 )..setPosition(-1.65, 1.05, 0.0),
68 )
69 ..add(
70 MeshNode(
71 DeviceMesh.upload(
72 context.device,
73 const TorusShape(
74 radius: 0.82,
75 tubeRadius: 0.34,
76 segments: 48,
77 tubeSegments: 24,
78 ).build(),
79 ),
80 _checkerMaterial,
81 name: 'checker torus',
82 )..setPosition(1.65, 1.05, 0.0),
83 )
84 ..add(
85 LightNode(name: 'key', intensity: 3.3)
86 ..setLocalForward(Vector3(-0.45, -0.82, -0.35)),
87 );
88 return scene;
89 }
91 @override
92 void verify(Scene scene, FrameResult frame) {
93 final Uint8List checker = _checker.encode().buffer.asUint8List();
94 final bool twoColours =
95 checker[0] != checker[_checker.cell * 4] ||
96 checker[1] != checker[_checker.cell * 4 + 1] ||
97 checker[2] != checker[_checker.cell * 4 + 2];
98 if (_solidMaterial.albedo == null ||
99 _checkerMaterial.albedo == null ||
100 !twoColours ||
101 frame.drawCalls < 2) {
102 throw StateError('the procedural textures were not drawn');
103 }
104 }