SADX Lantern Engine

Discussion in 'Engineering & Reverse Engineering' started by SF94, Dec 23, 2016.

  1. Twinbee MkII

    Twinbee MkII

    Uber Snuzzlemuffins Member
    I'm also having this issue and hope there's a solution.
     
  2. MainMemory

    MainMemory

    Kate the Wolf Tech Member
    4,525
    133
    43
    SonLVL
    Whoops, I totally forgot, Morph fixed it like a month ago, you can get a new release of CharSel that should fix it.
     
  3. Twinbee MkII

    Twinbee MkII

    Uber Snuzzlemuffins Member
    OMG Thank you! You're the best!
     
  4. Dude

    Dude

    Tech Member
    3,138
    0
    16
    Southbridge, MA
    Random VR/AR trash
    This is amazing. It really reinforces the notion that lighting is the foundation of graphics. I actually really like the DX assets, even moreso than the original dreamcast assets, when this lighting is used. Hopefully fixing that bottleneck isn't too challenging, but either way the mod as it stands makes it feel like a new game.
     
  5. E-122-Psi

    E-122-Psi

    Member
    2,092
    233
    43
    This is a great advancement, however it to me only opens up potential. Having a mod that emulates the Dreamcast's atmosphere is brilliant, but I'd be even more interested seeing Morph and co get creative with their own dynamic lighting, especially since DX can likely stretch effects much more on PC than Dreamcast.
     
  6. Codr

    Codr

    Member
    20
    0
    1
    Cyprus
    Huge secret ;)
    The transition between Sonic Adventure and Sonic Adventure DX was not so good in terms of shaders, everything just looked like it was made with plastic. I like this mod since, by the looks of it, it removes some of the plastic shading and makes it looks like the original game! Nice mod! :) :) :)
     
  7. BlazeHedgehog

    BlazeHedgehog

    A "Community Enigma"? Oldbie
    1,464
    6
    18
    Triggered a bug with this mod. Or, at least, I think it's a bug with this mod. I finished Tails' story and when it sent me back to the titlescreen, I got to the main menu and hit "Adventure", but my finger slipped and I hit cancel and confirm at the same time in such a way that it still sent me to the character selection menu but I heard the cancel sound play anyway.

    The end result is that all lighting became disabled and I had to quit the game and relaunch to make it come back

    [​IMG]
    [​IMG]
    [​IMG]

    The only other thing I can figure is that maybe the lighting state from the end of Tails' story also might have become stuck? Because it looks like he doesn't have lighting here, either

    [​IMG]

    Edit: trying to get the cancel-but-also-confirm thing to happen again and failing after several dozen times, I am inclined to believe maybe it really is related to Tails' lighting mode getting stuck after his story. Unfortunately that's harder to test :v:
     
  8. PkR

    PkR

    Member
    188
    18
    18
    SADX Dreamcast Conversion, The Emeralds' Awakening
    I've run into a very similar-looking issue while playing through Amy's story, but I couldn't reproduce it later either. It looks like it occurs when you're playing the game for a long time, e.g. beating the entire story of a character in one go without closing the EXE.
     
  9. Clownacy

    Clownacy

    Tech Member
    818
    54
    28
    Same. Thought it was a one-off issue for me. Happened around the same point in my playthough as well (Tails' end).
     
  10. SF94

    SF94

    Tech Member
    776
    3
    18
    Utah
    SA1/2 hax
    Hm, this isn't the first I've heard of this issue, but it seems to be really difficult to reproduce. If anyone can figure out a consistent way to reproduce it, please let me know. I'll be able to very easily track down the cause that way. Currently I've yet to run into this myself, much like the lightning shield bug.

    Edit: I've managed to narrow it down, and it's simple to see why it broke, but might be a bit of a hassle to fix. Pretty much the exact opposite of what I had hoped.
     
  11. BlazeHedgehog

    BlazeHedgehog

    A "Community Enigma"? Oldbie
    1,464
    6
    18
    Actually, the trigger for the bug might be fairly simple. It looks like if the game has to, at any point, load that main city area of Station Square during sunset, it breaks the lighting. It just happened again during Amy's story, and it happened directly following that map:

    [​IMG]
    [​IMG]

    I didn't get a screencap of the character select wheel but I can confirm that yes, the lighting was broken there, too, just like in the earlier image I posted. In both scenarios (after clearing Tails' story and escaping the Egg Carrier as Amy), the lighting became broken seemingly directly following Station Square at sunset.

    Edit: Oh, I didn't see that you had edited your post :v:

    Edit 2: Also, the "Station Square at Sunset" theory is broken because it doesn't effect Gamma

    [​IMG]
     
  12. SF94

    SF94

    Tech Member
    776
    3
    18
    Utah
    SA1/2 hax
    It seems to happen primarily when the scene switches from the egg carrier to station square (at least in this case). It then promptly tries to load the wrong palette file. Why it doesn't ever correct itself is beyond me, but this info certainly helps.
     
  13. BlazeHedgehog

    BlazeHedgehog

    A "Community Enigma"? Oldbie
    1,464
    6
    18
    Narrowing it down even further: it seems specifically to be because of the FMV sequence of the Egg Carrier exploding. It just happened again in Big's story, and that seems to be the one factor tying it all together.

    Maybe there IS no palette file for that sequence and it causes the whole system to barf?
     
  14. SF94

    SF94

    Tech Member
    776
    3
    18
    Utah
    SA1/2 hax
    Fixed! It has to do with a vertex normal scalar that SADX assigns values but doesn't actually use. Many objects in Red Mountain 2 use this to display properly, though (for example, the fire skull things), although they appear basically full bright in vanilla SADX since it doesn't use the values. Just as the FMV plays, it sets what is effectively an invalid value. I've now added a threshold for the normal scalar (FLT_EPSILON) to correct the issue. The fix will be available in the next update.
     
  15. SF94

    SF94

    Tech Member
    776
    3
    18
    Utah
    SA1/2 hax
    For those of you with performance issues that are willing to test the bleeding edge development builds, I'd appreciate it if you could give this build a try: https://ci.appveyor.com/project/SonicFreak94/sadx-dc-lighting/build/1.1.27/artifacts

    This build compiles shaders on the fly for each use case instead of switching effect techniques. On my system it significantly increased performance over the standard technique switching method. It has the potential to cause some stuttering during gameplay if a new shader needs to be compiled, but I plan to mitigate that by pre-compiling the most common use cases. In the Red Mountain example from a bit earlier in the thread, I now get 100% speed in the same scene.

    I'd appreciate performance reports!
     
  16. ezodagrom

    ezodagrom

    Member
    90
    0
    6
    If that's the same as the one linked here:
    https://ci.appveyor.com/project/SonicFreak94/sadx-dc-lighting/build/artifacts

    Saw the link in the description for update 3 of the dreamcast conversion mod, framerate improved alot on Red Mountain. ^^
     
  17. rata

    rata

    Member
    590
    19
    18
    Argentina
    Trying to be useful somehow.
    So, there is no chance of this working on a Sempron 3400+, right? I could try to play this game with this nice looking ligthing.
     
  18. SF94

    SF94

    Tech Member
    776
    3
    18
    Utah
    SA1/2 hax
    Grab the latest dev build and give it a go. It will probably be playable at least.
     
  19. SF94

    SF94

    Tech Member
    776
    3
    18
    Utah
    SA1/2 hax
    Version 1.2 has been released with a number of performance improvements and bug fixes!

    • Fixed various character materials (#23, #24).
    • Fixed palette selection for Hedgehog Hammer (#27).
    • Fixed a crash in Sky Deck related to a texture reference count oversight.
    • Fixed lighting breaking after certain FMVs.
    • Fixed a crash that occurred when switching between Chao Gardens (#37).
    • Implemented palette texture atlas for improved performance (#33, #38).
    • Implemented dynamic shader recompilation for significantly improved performance (#42).
    • Fixed some PL file selection oversights in the Egg Carrier adventure field (#46).
    • Fixed the Lightning Shield bug (#31).
    • Renamed to Lantern Engine.

    For the download and clickable issue/pull request numbers, click here.

    In addition to these changes, it has been enabled for automatic updates with the mod manager's new mod update system. You'll get change logs, automatic download and installation all from within the comfort of the mod manager. It never forces updates on you though, but I'll detail that in another post.
     
  20. SF94

    SF94

    Tech Member
    776
    3
    18
    Utah
    SA1/2 hax
    Version 1.3 has been released. Before trying it though, please make sure you update to the latest d3d8to9, or the game will pretty much immediately crash on the character select screen.

    • Implemented API for external mods to manipulate.
    • Improved overall accuracy (incl. palette selection).
    • Adjusted The Past's fire fading speed.
    • Fixed a bug in The Past causing blending to incorrect palettes (#45)
    • Fixed Sky Deck a million times over (incl. light direction). (#45, #54)
    • Implemented arbitrary index-to-index interpolation exposed to the API with separately controllable diffuse and specular blend indices.
    • Implemented individual diffuse and specular blend factors.
    • Improved compatibility for GeForce 6000 series cards. (#55)
    • Implemented improved character material fixes via the API material callback system. (#11)

    For new users, download/etc is here. For existing users, the Mod Loader should automatically update it for you. You can manually check for updates by right-clicking the mod in your mod list and clicking the update check button.

    For the programmers out there, I'll say right now that the API documentation needs work. If you'd like some examples, you can have a look at Obj_Past.cpp, which uses the API exclusively to perform its lighting effects.

    Here's a general overview of what the API can do:

    Control Uber-Shader Flags

    Using the API's function set_shader_flags, you have direct control over the flags used to select the correct shader for a given task. This is necessary when enabling palette blending. For example:

    Code (Text):
    1.  
    2. set_shader_flags(ShaderFlags_Blend, true);
    3.  
    This will enable palette blending. In the case of the blend flag, it must be explicitly disabled again by changing that last parameter to false. It will make no effort to disable it on its own.

    Override PL & SL Files

    This allows you to load your own palette or source light files for any given stage in the game. All you have to do is register a callback with pl_load_register and/or sl_load_register. Both of these functions take in a pointer to a function which must return const char* and receives two integers--one for the currently loading level, and one for the act.

    Material Callback System

    Using the material callback system, the mod will run a given function when a material is encountered that you requested to be notified of. This can be useful for specifically overriding diffuse and/or specular palettes temporarily on a per-material basis. I'll get to that in a moment.

    You can register a callback with the material callback system using material_register (and unregister with material_unregister). material_register takes in an array of NJS_MATERIAL pointers. These are pointers to materials that you want to be notified about. It also requires the length of that array followed by your callback function. Your callback function must return bool, and have two arguments: NJS_MATERIAL* material, and Uint32 flags. The latter is the same as the flags stored in the material, but with the global flow control overrides pre-applied (_nj_constant_attr_or_, _nj_constant_attr_and_) (if applicable).

    The return value of your callback function indicates how the API should proceed. If you return true, that indicates that you've "handled" that material and that it should stop running callbacks immediately. If you return false, it will continue running callbacks. So if you've made any changes using other available API functions and still return false, your changes can (and probably will) be overridden by another callback. The API runs callbacks in newest-to-oldest order.

    Diffuse & Specular Palette Override

    Using the functions set_diffuse and set_specular, you can override the diffuse and specular palette indices that are typically automatically selected by the mod. Both of these functions take two parameters: an integer in the range -1 to 7, and a boolean. The index is self-explanatory--it's the diffuse or specular index you want to override the default with. For reference:

    [​IMG]

    As you can see, the left column consists of 8 diffuse ("base") palettes, and the right column consists of 8 specular palettes.

    As for the second parameter (the boolean), it changes the duration of the override. Passing in false indicates that it will apply only for the duration of the material's use while rendering. As soon as rendering is complete with that material, the diffuse override is disabled. On the other hand, passing in true prevents the override from being disabled until you (or another mod!) explicitly disables it by passing in an index of -1.

    Blending

    Using the API, you can also create your own blending/fading effects. As mentioned earlier, a fantastic example of this would be Obj_Past.cpp. This is a stage-management object override, but that's not important. What is important are lines 34, lines 61-69, and lines 19-24 in that order.

    First and foremost, it enables the blending uber-shader flag during the initialization of the object:
    Code (Text):
    1.  
    2. // Enables palette blending in the shader.
    3. set_shader_flags(ShaderFlags_Blend, true);
    4.  
    which as mentioned, is a requirement for blending in general. Once the object has been properly initialized, it runs this code every frame:
    Code (Text):
    1.  
    2. // Blend both diffuse and specular index 0 to index 5.
    3. set_blend(0, 5);
    4. // Set the blend factor, where 0 is the source index and 1 is the target.
    5. set_blend_factor(f);
    6.  
    But let's focus on these lines for a moment:
    Code (Text):
    1.  
    2. // Blend both diffuse and specular index 0 to index 5.
    3. set_blend(0, 5);
    4.  
    As the comment describes, it blends both diffuse and specular indices 0 to 5. Or in other words, it blends the first palette to the 6th palette in each column respectively. To illustrate this, I'll use another screenshot of PLEdit:

    [​IMG]

    Now in order for the blending magic to actually occur, a blend factor is required. So next, let's focus on this line:

    Code (Text):
    1.  
    2. // Set the blend factor, where 0 is the source index and 1 is the target.
    3. set_blend_factor(f);
    4.  
    While the diffuse and specular blend factors can be controlled individually with set_diffuse_blend_factor and set_specular_blend_factor, The Past needs them both to blend at the same time. Thus, the convenience function set_blend_factor is used, which sets them both simultaneously.

    As the comment once again describes, a blend factor of 0.0 would mean that no blending occurs. In other words, palette index 0 would display as-is without change (as seen in the left column in this case, it would be 100% red). On the other hand, a blend factor of 1.0 would display the destination index unchanged. Anything in between will be a linear interpolation (or blend) between the two colors.

    The result: here

    Lastly, when the object is deleted, it disables the blending flag and resets all the blending indices so that nothing unexpected happens when something else needs to perform palette blending.

    Code (Text):
    1.  
    2. // Disable blending in the shader so it doesn't do extra work.
    3. set_shader_flags(ShaderFlags_Blend, false);
    4.  
    5. // Reset blend indices.
    6. set_blend(-1, -1);
    7.  
    Specifically, a source index (first parameter of set_blend) of -1 means that it will apply to all indices, i.e 0 to 7. A destination index of -1 however, disables blending for those indices.

    Pretty straightforward, right?