So, SubOffscreen, if you don't know already, is a sprite subroutine that checks whether a sprite is offscreen. If it is, it erases the sprite, though it will be reloaded if the sprite status is 08 or greater and if $161A,x isn't set to #$FF. The interesting part about it, though, is that it actually has multiple variants. You might have noticed that custom sprites with copy-pasted subroutines often have more than just one SubOffscreen there (even though none of them that I know of actually use more than one...just another reason why copy-pasted subroutines are a waste *grumble grumble*). Many have SubOffscreenX0, X1, X2, and X3, while some even have X4-X7 as well. The only difference between the different variants is how far offscreen a sprite has to be before it will despawn.
Now, in the original SMW, there are three ROM banks that contain sprites: banks 01, 02, and 03. And since even SMW copy-pastes sprite subroutines, albeit only 3 times instead of up to 192, each bank has its own copy of SubOffscreen (as well as GetDrawInfo and the like). But the three are NOT exactly the same. SubOffscreenX0 is identical in all three banks, but the other three variants actually differ, making for a total of 8 different variants. I'll still call them SubOffscreenX0-X7, though from what I've seen, sprites that list all 8 actually are missing SubOffscreenX4 and have an extra copy of X0. (As, I believe, does at least one version of my shared subroutine patch...that thing could use an update.) They are distinguished by these tables:
db $30,$C0,$A0,$C0,$A0,$F0,$60,$90,$A0,$70,$A0,$80,$A0,$40,$60,$B0 db $01,$FF,$01,$FF,$01,$FF,$01,$FF,$01,$FF,$01,$FF,$01,$00,$01,$FF
The first table is a series of low bytes, and the second is the corresponding high bytes. Both of them come in pairs, with one pair corresponding to each variant of the routine, the first byte for the right side of the screen and the second for the left. Oddly, the routine actually alternates which side it checks depending on the lowest bit of $13.
So, what does this mean for sprite coding? Well, as it turns out, the subroutine is simpler than I had originally thought. It's designed kind of oddly, but the important part is that those bytes in the tables indicate the range, from the left boundary (the second byte in each pair) to the right boundary (the first byte in each pair), as follows:
- SubOffscreenX0, known in SMW as "SubOffscreen0Bnk1", "SubOffscreen0Bnk2", and "SubOffscreen0Bnk3", is used by many sprites in banks 1, 2, and 3. It goes from -$40 to +$30 ($0130,$FFC0).
- SubOffscreenX1, known in SMW as "SubOffscreen1Bnk1" and "SubOffscreen1Bnk2", is used by the horizontal red Para-Koopa, checkerboard and flying rock platforms, line-guided sprites, and Big Boo in bank 1 and by the dolphins, Hammer Brother, and his platform in bank 2. It goes from -$40 to +$A0 ($01A0,$FFC0).
- SubOffscreenX2, known in SMW as "SubOffscreen2Bnk1", is used by the brown chained platform (sprite 5F). It goes from -$10 to +$A0 ($01A0,$FFF0).
- SubOffscreenX3, known in SMW as "SubOffscreen3Bnk1", is used by the Eeries. It goes from -$70 to +$60 ($0160,$FF90).
- SubOffscreenX4, known in SMW as "SubOffscreen2Bnk2", is used by the scale platforms. It goes from -$90 to +$A0 ($01A0,$FF70)
- SubOffscreenX5, known in SMW as "SubOffscreen1Bnk3", is not used by any sprites. It goes from -$80 to +$A0 ($01A0,$FF80).
- SubOffscreenX6, known in SMW as "SubOffscreen2Bnk3", is not used by any sprites. It goes from $40 to +$A0 ($0040,$01A0).
- SubOffscreenX7, known in SMW as "SubOffscreen3Bnk2" and "SubOffscreen3Bnk3", is used by the wall-following sprites, Ball 'n' Chain, and rotating gray platform in bank 2 and by the Mega Mole in bank 3. It goes from -$50 to +$60 ($FFB0,$0160).
The non-X0 variants are actually used by surprisingly few sprites, especially X2, X3, and X4, which are used by only one sprite each (well, technically two in the case of X3). But the really interesting one is SubOffscreenX6 (or SubOffscreen2Bnk3 if you prefer). Notice the lack of a sign on that first value? SubOffscreenX6 is the only variant that does not use a negative number for its second table value; it uses $0040 instead, which means that a sprite using it will actually count as offscreen even if it is 64 pixels away from the left screen boundary. I suppose it's not surprising that this one was never actually used for any sprites in SMW. Though SubOffscreenX5 (or SubOffscreen1Bnk3) doesn't have that excuse; its range is fairly ordinary, but no sprites ever used it either.
It's also worth noting that it is indeed possible to add custom values to the range table if you wanted a SubOffscreenX8 or something, and values greater than $01FF or less than $FF00 do still work properly. In fact, I may tweak that routine to where you can specify the range values manually if you give it the right inputs.
I'm working on a hack! Check it out here.