Sprite¶
Render textured quads via Sprite2D.
▶ Run in browserTags: 2d
Generates checkerboard, gradient, and star textures programmatically and
displays them as Sprite2D nodes. Demonstrates passing an RGBA uint8 ndarray
directly as the texture source (no file I/O), vertex-colour tinting, and
rotation animation.
Source¶
1"""Sprite: Render textured quads via Sprite2D.
2
3Generates checkerboard, gradient, and star textures programmatically and
4displays them as `Sprite2D` nodes. Demonstrates passing an RGBA uint8 ndarray
5directly as the texture source (no file I/O), vertex-colour tinting, and
6rotation animation.
7
8# /// simvx
9# web = { width = 900, height = 600 }
10# ///
11"""
12
13import math
14
15import numpy as np
16
17from simvx.core import Node2D, Sprite2D, Text2D, Vec2
18from simvx.graphics import App
19
20
21def _make_checkerboard(size: int = 64, cell: int = 8) -> np.ndarray:
22 img = np.zeros((size, size, 4), dtype=np.uint8)
23 for y in range(size):
24 for x in range(size):
25 if (x // cell + y // cell) % 2 == 0:
26 img[y, x] = [200, 60, 60, 255]
27 else:
28 img[y, x] = [60, 60, 200, 255]
29 return img
30
31
32def _make_gradient(size: int = 64) -> np.ndarray:
33 img = np.zeros((size, size, 4), dtype=np.uint8)
34 for x in range(size):
35 t = x / (size - 1)
36 r = int(255 * t)
37 g = int(255 * (1 - t))
38 img[:, x] = [r, g, 80, 255]
39 return img
40
41
42def _make_star(size: int = 64) -> np.ndarray:
43 img = np.zeros((size, size, 4), dtype=np.uint8)
44 cx, cy = size // 2, size // 2
45 for y in range(size):
46 for x in range(size):
47 dx, dy = x - cx, y - cy
48 dist = math.sqrt(dx * dx + dy * dy)
49 angle = math.atan2(dy, dx)
50 r = (size * 0.4) * (0.5 + 0.5 * abs(math.cos(2.5 * angle)))
51 if dist < r:
52 brightness = int(255 * (1 - dist / r))
53 img[y, x] = [255, 220, 50, brightness]
54 return img
55
56
57class SpriteScene(Node2D):
58 def on_ready(self):
59 self._time = 0.0
60 checker = _make_checkerboard()
61 gradient = _make_gradient()
62 star = _make_star()
63
64 self.checker = self.add_child(
65 Sprite2D(
66 texture=checker,
67 position=Vec2(200, 200),
68 width=128,
69 height=128,
70 name="Checker",
71 )
72 )
73 self.gradient = self.add_child(
74 Sprite2D(
75 texture=gradient,
76 position=Vec2(500, 200),
77 width=128,
78 height=128,
79 colour=(0.8, 1.0, 0.8, 1.0),
80 name="Gradient",
81 )
82 )
83 self.star = self.add_child(
84 Sprite2D(
85 texture=star,
86 position=Vec2(350, 400),
87 width=192,
88 height=192,
89 name="Star",
90 )
91 )
92 self.small_checker = self.add_child(
93 Sprite2D(
94 texture=checker,
95 position=Vec2(700, 400),
96 width=64,
97 height=64,
98 scale=Vec2(0.5, 0.5),
99 colour=(1.0, 1.0, 0.5, 0.8),
100 name="SmallChecker",
101 )
102 )
103 self.add_child(Text2D(text="Sprite2D Demo", position=(10, 10), font_scale=1.5, name="Title"))
104 self.add_child(Text2D(text="Checker | Gradient (tinted) | Star | Rotating", position=(10, 40), name="Info"))
105
106 def on_update(self, dt: float):
107 self._time += dt
108 self.star.rotation = self._time * 0.5
109 self.gradient.position = Vec2(500, 200 + 30 * math.sin(self._time * 2))
110
111
112if __name__ == "__main__":
113 App(width=900, height=600, title="SimVX Sprite2D Demo").run(SpriteScene())