@footgun/cobalt 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (131) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +18 -0
  3. package/bundle.js +284 -0
  4. package/cobalt2.jpeg +0 -0
  5. package/esbuild.js +20 -0
  6. package/examples/01-primitives/Game.js +8 -0
  7. package/examples/01-primitives/component-animation.js +8 -0
  8. package/examples/01-primitives/component-transform.js +13 -0
  9. package/examples/01-primitives/constants.js +6 -0
  10. package/examples/01-primitives/deps.js +2 -0
  11. package/examples/01-primitives/entity-sprite.js +47 -0
  12. package/examples/01-primitives/index.html +191 -0
  13. package/examples/01-primitives/system-renderer.js +37 -0
  14. package/examples/02-sprites/Game.js +8 -0
  15. package/examples/02-sprites/assets/spritesheet.json +6276 -0
  16. package/examples/02-sprites/assets/spritesheet.png +0 -0
  17. package/examples/02-sprites/assets/spritesheet_emissive.png +0 -0
  18. package/examples/02-sprites/component-animation.js +8 -0
  19. package/examples/02-sprites/component-transform.js +13 -0
  20. package/examples/02-sprites/constants.js +6 -0
  21. package/examples/02-sprites/deps.js +2 -0
  22. package/examples/02-sprites/entity-sprite.js +47 -0
  23. package/examples/02-sprites/index.html +310 -0
  24. package/examples/02-sprites/system-renderer.js +38 -0
  25. package/examples/03-tiles/Game.js +8 -0
  26. package/examples/03-tiles/assets/spelunky-tiles.png +0 -0
  27. package/examples/03-tiles/assets/spelunky0.png +0 -0
  28. package/examples/03-tiles/assets/spelunky1.png +0 -0
  29. package/examples/03-tiles/component-animation.js +8 -0
  30. package/examples/03-tiles/component-transform.js +13 -0
  31. package/examples/03-tiles/constants.js +6 -0
  32. package/examples/03-tiles/deps.js +2 -0
  33. package/examples/03-tiles/entity-sprite.js +47 -0
  34. package/examples/03-tiles/index.html +309 -0
  35. package/examples/03-tiles/system-renderer.js +38 -0
  36. package/examples/04-overlay/assets/spritesheet.json +22 -0
  37. package/examples/04-overlay/assets/spritesheet.png +0 -0
  38. package/examples/04-overlay/assets/spritesheet_emissive.png +0 -0
  39. package/examples/04-overlay/constants.js +6 -0
  40. package/examples/04-overlay/deps.js +1 -0
  41. package/examples/04-overlay/index.html +133 -0
  42. package/examples/05-bloom/Game.js +8 -0
  43. package/examples/05-bloom/assets/spritesheet.json +6276 -0
  44. package/examples/05-bloom/assets/spritesheet.png +0 -0
  45. package/examples/05-bloom/assets/spritesheet_emissive.png +0 -0
  46. package/examples/05-bloom/component-animation.js +8 -0
  47. package/examples/05-bloom/component-transform.js +13 -0
  48. package/examples/05-bloom/constants.js +6 -0
  49. package/examples/05-bloom/deps.js +2 -0
  50. package/examples/05-bloom/entity-sprite.js +47 -0
  51. package/examples/05-bloom/index.html +357 -0
  52. package/examples/05-bloom/system-renderer.js +38 -0
  53. package/examples/06-displacement/Game.js +8 -0
  54. package/examples/06-displacement/assets/displacement_map_repeat.jpg +0 -0
  55. package/examples/06-displacement/assets/spelunky-tiles.png +0 -0
  56. package/examples/06-displacement/assets/spelunky0.png +0 -0
  57. package/examples/06-displacement/assets/spelunky1.png +0 -0
  58. package/examples/06-displacement/component-animation.js +8 -0
  59. package/examples/06-displacement/component-transform.js +13 -0
  60. package/examples/06-displacement/constants.js +6 -0
  61. package/examples/06-displacement/deps.js +2 -0
  62. package/examples/06-displacement/entity-sprite.js +47 -0
  63. package/examples/06-displacement/index.html +350 -0
  64. package/examples/06-displacement/system-renderer.js +38 -0
  65. package/examples/07-sdl/assets/spritesheet.json +22 -0
  66. package/examples/07-sdl/assets/spritesheet.png +0 -0
  67. package/examples/07-sdl/assets/spritesheet_emissive.png +0 -0
  68. package/examples/07-sdl/main.js +109 -0
  69. package/examples/07-sdl/package.json +19 -0
  70. package/examples/08-light/Game.js +8 -0
  71. package/examples/08-light/assets/spelunky-tiles.png +0 -0
  72. package/examples/08-light/assets/spelunky0.png +0 -0
  73. package/examples/08-light/assets/spelunky1.png +0 -0
  74. package/examples/08-light/constants.js +6 -0
  75. package/examples/08-light/deps.js +2 -0
  76. package/examples/08-light/index.html +477 -0
  77. package/package.json +34 -0
  78. package/src/bloom/bloom.js +467 -0
  79. package/src/bloom/bloom.wgsl +176 -0
  80. package/src/cobalt.js +231 -0
  81. package/src/create-texture-from-buffer.js +39 -0
  82. package/src/create-texture-from-url.js +35 -0
  83. package/src/create-texture.js +46 -0
  84. package/src/deps.js +3 -0
  85. package/src/displacement/composition.wgsl +58 -0
  86. package/src/displacement/displacement-composition.ts +161 -0
  87. package/src/displacement/displacement-parameters-buffer.ts +44 -0
  88. package/src/displacement/displacement-texture.ts +221 -0
  89. package/src/displacement/displacement.js +160 -0
  90. package/src/displacement/displacement.wgsl +31 -0
  91. package/src/displacement/triangles-buffer.ts +95 -0
  92. package/src/fb-blit/fb-blit.js +161 -0
  93. package/src/fb-blit/fb-blit.wgsl +40 -0
  94. package/src/fb-texture/fb-texture.js +56 -0
  95. package/src/light/README.md +61 -0
  96. package/src/light/light.js +148 -0
  97. package/src/light/lights-buffer.ts +98 -0
  98. package/src/light/lights-renderer.ts +278 -0
  99. package/src/light/public-api.js +20 -0
  100. package/src/light/readme/01_illumination.webp +0 -0
  101. package/src/light/readme/02_lights_texture.webp +0 -0
  102. package/src/light/readme/03_lights_texture_decomposed.webp +0 -0
  103. package/src/light/readme/04_lights_texture_mask.webp +0 -0
  104. package/src/light/readme/05_lights_obstacle_decomposition.webp +0 -0
  105. package/src/light/readme/06_lights_hard_cast_shadows.webp +0 -0
  106. package/src/light/texture/lights-texture-initializer.ts +191 -0
  107. package/src/light/texture/lights-texture-mask.ts +286 -0
  108. package/src/light/texture/lights-texture.ts +121 -0
  109. package/src/light/types.ts +23 -0
  110. package/src/light/viewport.ts +63 -0
  111. package/src/overlay/constants.js +1 -0
  112. package/src/overlay/overlay.js +341 -0
  113. package/src/overlay/overlay.wgsl +88 -0
  114. package/src/primitives/constants.js +1 -0
  115. package/src/primitives/primitives.js +252 -0
  116. package/src/primitives/primitives.wgsl +54 -0
  117. package/src/primitives/public-api.js +325 -0
  118. package/src/scene-composite/scene-composite.js +168 -0
  119. package/src/scene-composite/scene-composite.wgsl +94 -0
  120. package/src/sprite/constants.js +1 -0
  121. package/src/sprite/create-sprite-quads.js +60 -0
  122. package/src/sprite/public-api.js +215 -0
  123. package/src/sprite/read-spritesheet.js +103 -0
  124. package/src/sprite/sorted-binary-insert.js +45 -0
  125. package/src/sprite/sprite.js +268 -0
  126. package/src/sprite/sprite.wgsl +103 -0
  127. package/src/sprite/spritesheet.js +212 -0
  128. package/src/tile/atlas.js +193 -0
  129. package/src/tile/tile.js +171 -0
  130. package/src/tile/tile.wgsl +105 -0
  131. package/src/uuid.js +3 -0
@@ -0,0 +1,309 @@
1
+ <!DOCTYPE html>
2
+ <html lang="en">
3
+ <head>
4
+ <meta charset="UTF-8" />
5
+ <title class="titleText">Web GPU prototyping</title>
6
+ <meta name="description" content="Web GPU 2d cobalt" />
7
+ <meta name="author" content="Michael Reinstein" />
8
+ <meta name="viewport" content="width=device-width" />
9
+ <meta name="viewport" content="initial-scale=1, maximum-scale=1" />
10
+
11
+ <meta name="apple-mobile-web-app-capable" content="yes" />
12
+ <meta name="mobile-web-app-capable" content="yes" />
13
+
14
+ <style>
15
+
16
+ body {
17
+ padding: 0;
18
+ margin: 0;
19
+ overscroll-behavior: none;
20
+ }
21
+
22
+ img {
23
+ image-rendering: -moz-crisp-edges;
24
+ image-rendering: -webkit-crisp-edges;
25
+ image-rendering: pixelated;
26
+ image-rendering: crisp-edges;
27
+ }
28
+
29
+ .viewport-container {
30
+ position: fixed;
31
+ top: 0;
32
+ left: 0;
33
+ bottom: 0;
34
+ right: 0;
35
+
36
+ display: flex;
37
+ align-items: center;
38
+ justify-content: center;
39
+ }
40
+
41
+ canvas {
42
+ background-color: green;
43
+ border: none;
44
+ image-rendering: -moz-crisp-edges;
45
+ image-rendering: -webkit-crisp-edges;
46
+ image-rendering: pixelated;
47
+ image-rendering: crisp-edges;
48
+ }
49
+
50
+ canvas::-webkit-scrollbar {
51
+ display: none;
52
+ }
53
+
54
+ </style>
55
+ </head>
56
+ <body>
57
+
58
+ <div class="viewport-container">
59
+ <canvas id="viewport" width="480" height="270"></canvas>
60
+ </div>
61
+
62
+ <script type="module">
63
+ import Game from './Game.js'
64
+ import * as Cobalt from '../../bundle.js'
65
+ import constants from './constants.js'
66
+ import dat from 'https://cdn.skypack.dev/pin/dat.gui@v0.7.9-2wtQAdFH5SRwnJLDWGNz/mode=imports,min/optimized/dat.gui.js'
67
+ import debounce from 'https://cdn.skypack.dev/pin/lodash.debounce@v4.0.8-4GXU9B066R3Th6HmjZmO/lodash.debounce.js'
68
+ //import animationSystem from './system-animation.js'
69
+ import rendererSystem from './system-renderer.js'
70
+ import spriteEntity from './entity-sprite.js'
71
+ import { ECS, vec2 } from './deps.js'
72
+
73
+
74
+ async function main () {
75
+
76
+ const canvas = document.querySelector('canvas')
77
+
78
+ const viewportWidth = constants.GAME_WIDTH
79
+ const viewportHeight = constants.GAME_HEIGHT
80
+ Game.renderer = await Cobalt.init(canvas, viewportWidth, viewportHeight)
81
+
82
+ // instantiate all resource nodes
83
+ const tileAtlasNode = await Cobalt.initNode(Game.renderer, {
84
+ type: 'cobalt:tileAtlas',
85
+ refs: { },
86
+ options: {
87
+ label: 'tile atlas',
88
+ tileSize: 16,
89
+ tileScale: 1.0,
90
+ textureUrl: 'assets/spelunky-tiles.png'
91
+ }
92
+ })
93
+
94
+ const hdrTex = await Cobalt.initNode(Game.renderer, {
95
+ type: 'cobalt:fbTexture',
96
+ refs: { },
97
+ options: {
98
+ label: 'hdr color texture',
99
+ format: 'rgba16float',
100
+ mip_count: 1,
101
+ viewportScale: 1.0,
102
+ usage: GPUTextureUsage.RENDER_ATTACHMENT | GPUTextureUsage.STORAGE_BINDING | GPUTextureUsage.TEXTURE_BINDING,
103
+ }
104
+ })
105
+
106
+ const emissiveTex = await Cobalt.initNode(Game.renderer, {
107
+ type: 'cobalt:fbTexture',
108
+ refs: { },
109
+ options: {
110
+ label: 'hdr emissive texture',
111
+ format: 'rgba16float',
112
+ mip_count: 1,
113
+ viewportScale: 1.0,
114
+ usage: GPUTextureUsage.RENDER_ATTACHMENT | GPUTextureUsage.COPY_DST | GPUTextureUsage.TEXTURE_BINDING,
115
+ }
116
+ })
117
+
118
+ const bloomTex = await Cobalt.initNode(Game.renderer, {
119
+ type: 'cobalt:fbTexture',
120
+ refs: { },
121
+ options: {
122
+ label: 'hdr bloom texture',
123
+ format: 'rgba16float',
124
+ mip_count: 7,
125
+ viewportScale: 0.5,
126
+ usage: GPUTextureUsage.RENDER_ATTACHMENT | GPUTextureUsage.STORAGE_BINDING | GPUTextureUsage.TEXTURE_BINDING,
127
+ }
128
+ })
129
+
130
+ const bloomNode = await Cobalt.initNode(Game.renderer, {
131
+ type: 'cobalt:bloom',
132
+ refs: {
133
+ // key is the var name defined in this node
134
+ // value is the var name in the cobalt resources dictionary
135
+ emissive: emissiveTex,
136
+ hdr: hdrTex,
137
+ bloom: bloomTex
138
+ },
139
+ options: {
140
+ // any extra options you want to pass to this node
141
+ bloom_intensity: 45.0,
142
+ bloom_combine_constant: 0.3,
143
+ bloom_knee: 0.2,
144
+ bloom_threshold: 0.1, // 1.0
145
+
146
+ // sprite instance 1
147
+ sprite_instances: [
148
+ {
149
+ emissive_intensity: 1.0,
150
+ },
151
+ {
152
+ emissive_intensity: 0.5,
153
+ },
154
+ ],
155
+ }
156
+ })
157
+
158
+ const tmpTex = await Cobalt.initNode(Game.renderer, {
159
+ type: 'cobalt:fbTexture',
160
+ refs: { },
161
+ options: {
162
+ label: 'bloom + hdr compositing',
163
+ format: 'bgra8unorm',
164
+ mip_count: 1,
165
+ viewportScale: 1.0,
166
+ usage: GPUTextureUsage.RENDER_ATTACHMENT | GPUTextureUsage.COPY_DST | GPUTextureUsage.TEXTURE_BINDING,
167
+ }
168
+ })
169
+
170
+ // instantiate all runnable nodes
171
+ const tileNode = await Cobalt.initNode(Game.renderer, {
172
+ type: 'cobalt:tile',
173
+ refs: {
174
+ // key is the var name defined in this node
175
+ // value is the var name in the cobalt resources dictionary
176
+ tileAtlas: tileAtlasNode,
177
+ hdr: hdrTex,
178
+ },
179
+ options: {
180
+ textureUrl: 'assets/spelunky1.png',
181
+ scrollScale: 0.6,
182
+ //zIndex: 0,
183
+ }
184
+ })
185
+
186
+ const tileNode2 = await Cobalt.initNode(Game.renderer, {
187
+ type: 'cobalt:tile',
188
+ refs: {
189
+ // key is the var name defined in this node
190
+ // value is the var name in the cobalt resources dictionary
191
+ tileAtlas: tileAtlasNode,
192
+ hdr: hdrTex,
193
+ },
194
+ options: {
195
+ textureUrl: 'assets/spelunky0.png',
196
+ scrollScale: 1.0,
197
+ //zIndex: 5,
198
+ }
199
+ })
200
+
201
+
202
+ const compositeNode = await Cobalt.initNode(Game.renderer, {
203
+ type: 'cobalt:composite',
204
+ refs: {
205
+ hdr: hdrTex,
206
+ bloom: bloomTex,
207
+ combined: tmpTex,
208
+ },
209
+ options: { }
210
+ })
211
+
212
+
213
+ const b = await Cobalt.initNode(Game.renderer, {
214
+ type: 'cobalt:fbBlit',
215
+ refs: {
216
+ in: tmpTex,
217
+ out: 'FRAME_TEXTURE_VIEW',
218
+ },
219
+ options: { }
220
+ })
221
+
222
+
223
+ // use resizeViewport to init values on load:
224
+ resizeViewport(Game.renderer, window.innerWidth, window.innerHeight)
225
+
226
+ // window resize is *expensive* - best to debounce:
227
+ const debouncedResize = debounce(function () {
228
+ resizeViewport(Game.renderer, window.innerWidth, window.innerHeight)
229
+ }, 50)
230
+
231
+ window.addEventListener('resize', debouncedResize, { passive: true })
232
+
233
+
234
+
235
+ const world = ECS.createWorld()
236
+ ECS.addSystem(world, rendererSystem(Game.renderer))
237
+
238
+ Cobalt.setViewportPosition(Game.renderer, [ 240, 135 ])
239
+
240
+ ECS.addSystem(world, function cameraLoopSystem(world) {
241
+ const onUpdate = function (dt) {
242
+ const elapsed = performance.now()
243
+ const x = (Math.sin(elapsed / 2000) * 0.5 + 0.5) * 128
244
+ const y = (Math.sin(elapsed / 5000) * 0.5 + 0.5) * 170
245
+
246
+ //const { tileScale } = Game.renderer.tile
247
+
248
+ Cobalt.setViewportPosition(Game.renderer, [ x, y ])
249
+ }
250
+
251
+ return { onUpdate }
252
+ })
253
+
254
+ Game.world = world
255
+
256
+
257
+ const gameLoop = function () {
258
+ tick(Game)
259
+ requestAnimationFrame(gameLoop)
260
+ }
261
+
262
+
263
+ requestAnimationFrame(gameLoop)
264
+ }
265
+
266
+
267
+ function tick (context) {
268
+ const newTime = performance.now()
269
+ const frameTime = newTime - context.lastFrameTime
270
+ context.lastFrameTime = newTime
271
+ ECS.update(context.world, frameTime)
272
+ ECS.cleanup(context.world)
273
+ }
274
+
275
+
276
+ function resizeViewport (renderer, width, height) {
277
+
278
+ const { canvas, device } = renderer
279
+
280
+ // determine which screen dimension is most constrained
281
+ // we floor the render scale to an integer because we get weird texture artifacts when trying to render at
282
+ // certain float values (e.g., 3.0145833333333334)
283
+ const renderScale = Math.floor(Math.min(width/constants.GAME_WIDTH, height/constants.GAME_HEIGHT))
284
+
285
+ canvas.width = Math.ceil(constants.GAME_WIDTH)
286
+ canvas.height = Math.ceil(constants.GAME_HEIGHT)
287
+
288
+ Cobalt.setViewportDimensions(renderer, constants.GAME_WIDTH, constants.GAME_HEIGHT)
289
+
290
+ // https://www.khronos.org/webgl/wiki/HandlingHighDPI
291
+ // webgl display resolution size within canvas
292
+ const resolution = window.devicePixelRatio || 1
293
+
294
+ // center the canvas if native window doesn't match aspect ratio
295
+ canvas.style.width = canvas.width * renderScale + 'px'
296
+ canvas.style.height = canvas.height * renderScale + 'px'
297
+
298
+ canvas.style.left = Math.round((width - canvas.width * renderScale) / 2) + 'px'
299
+ canvas.style.top = Math.round((height - canvas.height * renderScale) / 2) + 'px'
300
+ }
301
+
302
+
303
+ main()
304
+
305
+ </script>
306
+
307
+
308
+ </body>
309
+ </html>
@@ -0,0 +1,38 @@
1
+ import * as Cobalt from '../../bundle.js'
2
+ import Game from './Game.js'
3
+ import { ECS } from './deps.js'
4
+
5
+
6
+ const SPRITE_QUERY = [ 'sprite' ]
7
+
8
+
9
+ // @param Object renderer Cobalt render state
10
+ export default function createRendererSystem (renderer) {
11
+
12
+ // temporary variables, allocated once to avoid garbage collection
13
+ const buf = new Float32Array(136) // tile instance data stored in a UBO
14
+ const removedEntities = {
15
+ count: 0,
16
+ entries: new Array(100)
17
+ }
18
+
19
+ return function rendererSystem (world) {
20
+
21
+ const onUpdate = function (/*dt*/) {
22
+
23
+ const device = renderer.device
24
+ const context = renderer.context
25
+
26
+ ECS.getEntities(world, SPRITE_QUERY, 'removed', removedEntities)
27
+
28
+ for (let i=0; i < removedEntities.count; i++) {
29
+ const oldSprite = removedEntities.entries[i]
30
+ oldSprite.spriteNode.removeSprite(oldSprite.sprite.cobaltSpriteId)
31
+ }
32
+
33
+ Cobalt.draw(Game.renderer)
34
+ }
35
+
36
+ return { onUpdate }
37
+ }
38
+ }
@@ -0,0 +1,22 @@
1
+ {
2
+ "frames": {
3
+ "health-0.png":
4
+ {
5
+ "frame": {"x":924,"y":369,"w":14,"h":15},
6
+ "rotated": false,
7
+ "trimmed": false,
8
+ "spriteSourceSize": {"x":0,"y":0,"w":14,"h":15},
9
+ "sourceSize": {"w":14,"h":15}
10
+ }
11
+
12
+ },
13
+ "meta": {
14
+ "app": "https://www.codeandweb.com/texturepacker",
15
+ "version": "1.0",
16
+ "image": "spritesheet.png",
17
+ "format": "RGBA8888",
18
+ "size": {"w":1024,"h":1024},
19
+ "scale": "1",
20
+ "smartupdate": "$TexturePacker:SmartUpdate:b764ee9c12c5dc939f41397531cf84b9:41d72789a4b56c697e70e42eff410840:729adc6043343cfda41c447ce8f464d6$"
21
+ }
22
+ }
@@ -0,0 +1,6 @@
1
+
2
+ export default {
3
+ // virtual game screen dimensions in 16:9
4
+ GAME_WIDTH: 480,
5
+ GAME_HEIGHT: 270,
6
+ }
@@ -0,0 +1 @@
1
+ export { mat4, vec2, vec3, vec4 } from 'https://wgpu-matrix.org/dist/3.x/wgpu-matrix.module.js'
@@ -0,0 +1,133 @@
1
+ <!DOCTYPE html>
2
+ <html lang="en">
3
+ <head>
4
+ <meta charset="UTF-8" />
5
+ <title class="titleText">Web GPU prototyping</title>
6
+ <meta name="description" content="Web GPU 2d cobalt" />
7
+ <meta name="author" content="Michael Reinstein" />
8
+ <meta name="viewport" content="width=device-width" />
9
+ <meta name="viewport" content="initial-scale=1, maximum-scale=1" />
10
+
11
+ <meta name="apple-mobile-web-app-capable" content="yes" />
12
+ <meta name="mobile-web-app-capable" content="yes" />
13
+
14
+ <style>
15
+
16
+ body {
17
+ padding-inline: 40px;
18
+ margin: 0;
19
+ overscroll-behavior: none;
20
+ }
21
+
22
+ img {
23
+ image-rendering: -moz-crisp-edges;
24
+ image-rendering: -webkit-crisp-edges;
25
+ image-rendering: pixelated;
26
+ image-rendering: crisp-edges;
27
+ }
28
+
29
+ .viewport-container {
30
+ position: fixed;
31
+ top: 0;
32
+ left: 0;
33
+ bottom: 0;
34
+ right: 0;
35
+
36
+ display: flex;
37
+ align-items: center;
38
+ justify-content: center;
39
+ }
40
+
41
+ canvas {
42
+ background-color: green;
43
+ border: none;
44
+ image-rendering: -moz-crisp-edges;
45
+ image-rendering: -webkit-crisp-edges;
46
+ image-rendering: pixelated;
47
+ image-rendering: crisp-edges;
48
+ }
49
+
50
+ canvas::-webkit-scrollbar {
51
+ display: none;
52
+ }
53
+
54
+ </style>
55
+ </head>
56
+ <body>
57
+ <h1>Overlay Nodes</h1>
58
+ <p>
59
+ When building UIs, it's helpful to place sprites on a layer that uses the traditional
60
+ cartesian coordinate system, where 0,0 is the top left corner and GAME_WIDTH, GAME_HEIGHT is the bottom right corner.
61
+ </p>
62
+ <div class="viewport-container">
63
+ <canvas id="viewport" width="480" height="270"></canvas>
64
+ </div>
65
+
66
+ <script type="module">
67
+ import * as Cobalt from '../../bundle.js'
68
+ import constants from './constants.js'
69
+ import { vec2, vec3, vec4 } from './deps.js'
70
+
71
+
72
+ async function main () {
73
+
74
+ const canvas = document.querySelector('canvas')
75
+
76
+ const viewportWidth = constants.GAME_WIDTH
77
+ const viewportHeight = constants.GAME_HEIGHT
78
+ const renderer = await Cobalt.init(canvas, viewportWidth, viewportHeight)
79
+
80
+ // instantiate all resource nodes
81
+ const spritesheet = await Cobalt.initNode(renderer, {
82
+ type: 'cobalt:spritesheet',
83
+ refs: { },
84
+ options: {
85
+ spriteSheetJsonUrl: './assets/spritesheet.json',
86
+ colorTextureUrl: 'assets/spritesheet.png',
87
+ emissiveTextureUrl: 'assets/spritesheet_emissive.png'
88
+ }
89
+ })
90
+
91
+ const overlayNode = await Cobalt.initNode(renderer, {
92
+ type: 'cobalt:overlay',
93
+ refs: {
94
+ // key is the var name defined in this node
95
+ // value is the var name in the cobalt resources dictionary
96
+ spritesheet: spritesheet,
97
+ color: 'FRAME_TEXTURE_VIEW',
98
+ },
99
+ options: { }
100
+ })
101
+
102
+
103
+ // test sprites
104
+ overlayNode.addSprite('health-0.png', // name
105
+ [ 20, 20 ], // position
106
+ vec3.create(1, 1, 1),
107
+ vec4.create(0, 0, 0, 0), // tint
108
+ 1.0, // opacity
109
+ 0, // rotation
110
+ //zIndex
111
+ )
112
+
113
+ overlayNode.addSprite('health-0.png', // name
114
+ [ 420, 220 ], // position
115
+ vec3.create(1, 1, 1),
116
+ vec4.create(0, 0, 0, 0), // tint
117
+ 1.0, // opacity
118
+ 0, // rotation
119
+ //zIndex
120
+ )
121
+
122
+ Cobalt.setViewportDimensions(renderer, constants.GAME_WIDTH, constants.GAME_HEIGHT)
123
+ Cobalt.draw(renderer)
124
+ }
125
+
126
+
127
+ main()
128
+
129
+ </script>
130
+
131
+
132
+ </body>
133
+ </html>
@@ -0,0 +1,8 @@
1
+ // all of the example's globals are consolidated here
2
+ export default {
3
+ renderer: undefined, // cobalt instance
4
+ world: undefined, // ECS instance
5
+
6
+ // timekeeping (in milliseconds)
7
+ lastFrameTime: 0, // local time the last frame ran
8
+ }