A few months ago Ashley made a post on how to handle multiple lights in a single layout (for reference: https://www.scirra.com/tutorials/5005/multiple-colored-shadow-casting-lights)
This approach may work for some, but I found the method described to be extremely limiting, due to a number of factors:
- Not all lighting necessarily needs to be realtime, and lights that are just used to set mood would be wasting processing time since they re-render every frame for every light.
- Dealing with a lot of lights becomes extremely cumbersome as more layers are added.
- Because of limitations in how C2 handles shaders in WebGL, if a developer wanted soft lights, they would have to apply a blur effect to a LOT of layers, destroying performance.
- Any visual effects lighting, like the flash of an explosion of a player throws a grenade, would have severe limitations, due to needing to juggle layers, with the number of available layers creating a hard limit on how many lights could be used.
- If all stages take place in a single layout (eg. loading multiple tilemaps within a single layout for various stages), the layer management issue becomes very convoluted to manage, and has a hard limit on how many lights can appear in any stage - and hard limits are bad.
- In a production environment where you may be working with a team, it simply isn't an option to expect level designers or artists to have to work in the same program/files as the developer. This is a reality of game development that gets ignored a lot, but that doesn't make it any less true.
So, with that in mind, I set about creating a way to manage multiple C2-native Shadow Lights on as few layers as possible. There were some issues initially because of a bug in the tilemap collisions, but Ashely has fixed this in r240 beta and I've been able to make some progress:
Using a simple test layout:
Which looks like this in the browser without lighting being applied properly because they're all on the same layer:
And looks like this in the browser with my solution applied. So far, I've ended up using 3 layers for background, foreground and VFX lighting. Static lighting only needs to render once, eliminating any overhead from having to redraw multiple shadows & layers every frame, and dynamic lighting only has to render when it's being interacted with, such as the light moving/rotating or objects that cast shadows overlapping it. VFX lights render for a single tick and then are removed, so they don't really impact performance very much at all:
Play with the example yourself (arrows move/jump, ctrl/shift shoot and drop grenades respectively):
https://dl.dropboxusercontent.com/u/14245368/C2/LightingTest/index.html
It's not quite ready for use in a production environment, and it needs a lot more flexibility to blend well with artwork and provide the kind of features people typically expect from a lighting system, but as a proof of concept created in a few hours it shows what might be possible. It DOES currently involves the use of the Paster plugin, which is unavoidable; rendering to a texture quickly is really a feature that should be native to C2, but somehow it isn't, which seems like a huge oversight, so there's no way to do it without any 3rd-party add-ons at this time. Some of the shaders could also be optimized if there were a way for the shader to sample the screen at a lower resolution, but I haven't been able to get that to work in C2 at all (which seems like a bug in C2).
I think there's a lot more optimization that can be done, so I'd be curious to hear what kind of performance you're getting if you're on a PC with a slower GPU/integrated graphics.
The end goal is to create a flexible lighting system that's easy to use. I'll update this post as I tweak things and to flesh out what's going on behind the scenes a bit more.