Published on 19th August 2024
Welcome to Phaser World Issue 193
This week's issue is packed with interesting links as usual: Rapier Physics available in Phaser, new tutorial series exploring how to build a space shooter game, our Dev Logs full of juicy, animating details of what we're currently working on, and of course some cool Phaser games you can play directly in your browser!
Game of the Week
Amazing Jewels
Drop and rotate jewels to crush them into ever higher bonus points in this highly polished and addictive match 3 outing.
Wizlympics
The Olympic fun continues with Wizlympics 2024!
Härveli
You need to get the red ball to the pink goal area. You can build sticks, wheels, spinning wheels and magic beams.
Rapier Physics and Phaser Templates
Quickly get up and running using Rapier Physics directly in Phaser with our two new Project Templates and 30 source code examples.
Learn to make a space shooter in Phaser 3
Profilic Phaser creator Scott Westover is creating a new tutorial series!
Star History Monthly July 2024 | Fun AI Generators
For this edition, we present some fun ideas of AI generators that have done well in broadening the boundaries of AI's application.
ASMR Programming - Flappy Bird (TypeScript + Phaser) - No talking
Enjoy the gentle sounds of keyboard clicks and mouse movements as I guide you through the coding process step-by-step.
Francisco: Hi everyone!
This week, I’ve been working on adapting Rapier, a 2D and 3D physics engine created in Rust that can be used in JavaScript thanks to its compilation to WebAssembly (wasm). I’ve also been preparing some examples for Rapier and the rapier-connector, and I’m excited to announce that the first version of rapier-connector is now available on npm! You can check it out here: https://www.npmjs.com/package/@phaserjs/rapier-connector.
If you’re interested in seeing the rapier-connector in action, you can view the examples here: https://phaser.io/sandbox/full/GcQ31KLH.
Can: Hey all,
This week, I made a decent progress in refining our particle system by integrating it seamlessly with our animation system, despite it's still in early stage, it's going well. My primary focus has been on balancing simplicity with performance, ensuring the system is not only efficient but also flexible enough to progress. I’m excited to share a sneak peek of the demo, showcasing this new functionality in action!
Arian: Hello!
This week we finished polishing the asset import experience in the editor. You can now drop a folder into the editor and it will create the entire sub-folder structure in the project. We also made improvements to the Add Files section of the Inspector view, so you can drop files into a given folder.
This week we also started developing new features, such as providing more information about the editor updates. That is, when you run the editor, it connects to our update server and checks how many updates are available, and displays a message with that information. Something like: "You are 3 updates behind".
But the most exciting thing we've done this week is... starting to implement a new trial of the editor! At the moment, I can't give more information about it, but I didn't want to overlook it since it's a task we'll be working on for a while.
Ben: 2024-08-16
I've been planning an upgrade to Tiles for a while now. So what happened? This week turned out to be dedicated to a rewrite of the shader system in the Beam renderer. Of course!
This was an important step for supporting further work, however. Beam includes a lot of improved shaders. We've got lighting, lighting with self-shadowing, lighting on flat polygons, rotating TileSprites, plain old texturing, and a whole lot more. And as development continues, we keep adding new variants. As discussed last week, looking at tiles reveals all sorts of issues with seams and borders. We've even got ideas for variants that support antialiased pixel art (thanks flay!).
But that's a lot of shaders. And these options can combine, creating a branching family of variant shaders. It just isn't practical to write up every possible variant - we'd have hundreds of shaders. Phaser would blow up in size, and users would only need a handful of those variants.
And there are even issues with the existing shader code. For example, the Multi shader responsible for rendering ordinary sprites is called "Multi" because it has multiple textures - but how many depends on the hardware capabilities of the system. So the existing shader has the phrase %forloop% embedded in it, so we can process and replace it with the appropriate code. But this isn't valid GLSL (the shader language used to write WebGL shaders). It's a small thing, but when we're editing shaders, it would be nice for them to have valid code, so our editors can do their job and look for errors or unused variables and what not.
So we've come up with a better way of handling shaders.
My objectives were:
- Use valid GLSL code everywhere.
- Facilitate modular reuse of code.
- Keep the code as close together as possible, so even when code is broken up across modules, developers don't get too lost.
- Don't use massive IF...ELSE blocks to configure shader behavior, because everybody will yell at me for branching on the GPU.
- Don't flood the system with new shaders.
- Create shaders only when they're needed for rendering
We achieved this through a few systems:
- The GLSL preprocessor.
- Shader factories.
- Shader managers.
The GLSL preprocessor is a language inside a language. This isn't code that runs when you run the program; it's code that runs when you compile the program. It looks like #define SHADERNAME MYSHADER, starting commands with # and using a limited instruction set. Modern languages like Zig and Rust do a lot with compile-time execution, but GLSL is based on C++, with extra restrictions to run on the Web.
We developed two conventions for preprocessor usage: feature flags, and template pragmas.
Feature flags combine #define FEATURE_X with #ifdef FEATURE_X...#endif blocks. This lets us turn sections of code on or off by setting a simple list of features. This is simple, but it can make a huge difference. We've seen highly complex experimental shaders refuse to compile on low-end iPhones, until we used feature flags to turn off most of that complexity.
Template pragmas use #pragma phaserTemplate(location) to identify a location in the code. The #pragma command is intended for talking to the compiler in ways the language doesn't define, which is exactly what we're doing. It doesn't actually do anything in GLSL (other than raise a silent warning). However, it is valid GLSL, so we can stick it in our code and keep editing. Then we can replace the pragmas with other code, in our own compilation step before sending the shader to the GPU.
Our compilation happens in a shader factory. This takes a base shader, a list of additions, and a list of features. It then inserts the additions and features into the base shader, replacing the template pragmas. The additions consist of a name, a list of locations, and some GLSL code to add to each location. Thus, an addition can make a lot of changes. Additions also combine their names, creating a unique key for each texture variant. This ensures we don't create duplicate shaders.
Shader managers live in RenderNodes. They listen to requests for shader features, and at render time, they provide the shader program that meets the current needs. They also abstract the need to set uniforms directly on a specific shader program. This ensures that we only create shaders which are needed for rendering; instead of initializing 31 core shaders, as the old pipeline system does, we can initialize just 1 or 2.
Taken together, this means we can keep our code complexity down, while making our shaders more powerful than ever. And that's great for package size, which is great for game load time.
So the last thing I did today was delete 23 files. We're removed several thousand lines of code (and written a few thousand more, but it's still less). That's a lot of boilerplate and duplicate code that we can just eliminate. Any time I can delete that much of my own code, it's a good day.
Next up, we use this system to improve tiles! We've got some very exciting ideas for improving tile rendering - and maybe other sorts of rendering too. I even created files for them last week, but then I realized I would need to create more files to support different shader variants, and that's why this week happened...
Phaser Releases
Phaser 3.85.0 Beta 2 released 23rd July 2024.
Phaser Editor 4.2 released 7th August 2024.
Phaser CE 2.20.0 released 13th December 2022.
Have some news you'd like published? Email support@phaser.io or tweet us.
Missed an issue? Check out the Back Issues page.
©2024 Phaser Studio Inc | 548 Market St PMB 90114, San Francisco CA 94104