It's one of the key mechanics I'd like to bring into my new game: being able to catch hanging things and hanging as well. It was a fun move in Commander Keen, it was amazingly expanded in Fury of the Furries and Mickey Magical quest ... And last week-end, I went on to try and
get it prototyped.
I started with a summary of how Bilou can hang below spongebops in School Rush ... something we don't see a lot in the blog, mostly because Bilou is supposed to *ride* the sponges, not hang under them. Hanging was added as an "else" branch of another "else" branch:
when you hit the "HANDS" button mid-air, Bilou does a roll move trying to grab what's nearby. that is AIRGRAB state. The original idea was to test what was *below* him and either pick-up a dumblador or ride a spongebop... but the move shows the hand grabbing in front and rear directions as well ... so it would feel natural that Bilou could grab a sponge even if he's on the same horizontal line, like in the sketch on the left. Yet, snapping Bilou on top of the sponge from this location felt glitchy.
Bon, j'ai un p'tit Bilou suspendu sur une page de mon cahier-agenda depuis le début 2024 ... j'en ai un autre sur la bannière du blog ... je crois que l'appel du pied est assez clair: il serait temps de prototyper un peu ça, d'autant que cette fois ci, ce ne sont pas les coins de niveau où s'accrocher qui manquent dans le livre-secret-du-level-design.
Et pour "commencer simple", l'idée était de faire subir à Bilou le comportement des éponges. tout en réutilisant un des états codés pour l'interaction avec les éponges: rester suspendu (la feinte). Chose qui m'a tout de même demandé de me replonger dans pas mal de gobscript, parce qu'à la base, il est prévu que Bilou s'accroche *par-dessus* les éponges, et pas qu'il pende en-dessous. Le côté "pendu" n'a été rajouté que dans les derniers 20% du projet, entre deux séances de playtesting parce "bin, oui, c'est vrai au fait: pourquoi Bilou ne pourrait-il pas rester suspendu s'il était trop bas pour escalader l'éponge au moment ou la joueuse a appuyé sur (B) ?"
So instead, Bilou will enter AIRHOP move, getting an automatic double jump and automatically tracking the sponge's position. That feels fairly naturally when playing, that gives you a sort of "fair second chance" but it might fail anyway: you may fall below sponge's position again without having reached the "riding spot", with no hope of catching up. and *that* is the time when we finally switch to HANGING.

There will be other objects to hang to in the game, especially bookmarks, vines, and the like. Some of them could be entities like spongebop (maybe moving a bit less), but sometimes it might also be nice to have tiles you can hook to. I have code to make some tiles react to collisions with the player, but that was not enough: the hitboxes used to detect spongebop explicitly search for baddies. And because I'm testing 3 areas over the course of the animation, I'm out of options to also test for friendly areas (which has been the case for all pick-ups so far ^^"). But hitting a tile can trigger an animation, and it can spawn an entity with proper hitboxes so that Bilou could hook to *that*. You couldn't really hook to a tile, anyway, because the BlockArea created during the collision test is immediately recycled, so you could not attach to it.
Mon idée était ensuite d'utiliser un type de bloc spécial pour servir de point d'accroche, et d'aller "poker" quelques blocs de ce genre à des endroits bien sentis de la map "green" de la démo. ça non plus, ça n'a pas fonctionné comme j'espérais. Entre autres parce que quand Bilou cherche à s'accrocher à quelque-chose pendant sa pirouette-en-l'air, il cherche parmi la liste "EVIL" ... et les blocs interactifs, eux se présente automatiquement comme des "HERO".
Bon, ce n'est pas bien grave: puisque je voulais que Bilou s'attache au point d'ancrage, il fallait de toutes façons que j'introduise un GOB (game object) généré à partir du bloc spécial, un peu comme les scintillements qui suivent Bilou quand on ramasse un smiley bleu. Ce gob pourra être dans la liste que l'on veut. Pour éviter qu'on ne génère des quantités ridicules de gob-points-d'ancrage, on va (enfin) utiliser une animation de la map elle-même pour désactiver puis réactiver les propriétés du bloc pendant que le gob est présent. Exactement le comportement des blocs-question de SuperMario quand on les coup-de-boulise.

So the plan was the following: a new special block that would react to GRAB action. When that happens, it trigger the animation that actually leaves graphics untouched (with "spr0 ffff") but turns the physical tile into "plain fall-through" for 5 frames, and then restore the tile as "block 07" (thus interactive) again. Quite the kind of thing that SuperMario question blocks
do on a daily basis, actually.
(It turned out meanwhile that using sprite 'ffff' did not work as intended, so I ended up adding a bbox statement to that animation -- effectively making it a special 8x8 tile rather than a 16x16 special block -- and fixed the code that plays mapanim so that "props" instruction is executed immediately rather than cached until the next "spr0" instruction)
anim9 spr:2 {
spr0 7 # visuals for the "tile replacement",
delay 5 # here just a Bilou hand ...
done
}
state63 :anim9 { # behaviour for that hand :
using freemove # just stay there,
area 0 (0,0)-(8,8) 1010 # accept GRAB hits.
}
state62 :anim9 { # should have been the persistent state when Bilou hooked...
using freemove
}
state63->state62 on found 0 [wc $1010 ?] (t) # detecting the actual hook-up hit
state63->nil on done # and disappear otherwise
using shgob(state63 is e:=1:6) as 6 # a special action to spawn the hooked hand
# oh ... and it's an evil hooked hand.
block 06 {
is gndhook "ff3c7cfebe2a2a00" # the special tile
area (0,0)-(7,7) 1010 # will also detect GRAB hits
on hit [t] (x6) :anim6 # and the 'x6' will invoke shgob registered 'as 6'
props fc0
}
That should have done it. I could see the hand showing up, and getting away, but I couldn't ever hook to it. I couldn't get an evidence of why it failed, but I believe it is rooted to the fact that bilou's own bbox must overlap the tile in order to trigger the "on hit" transition. but since all the hitboxes with the GRAB flag tend to be off-center, the second collision (with state63 entity) doesn't occur because there's no overlap.
Alors oui, je vous balance le script directement dans le browser. Parce que ça ne fonctionne pas. Enfin, après avoir corrigé la gestion de l'animation pour ne pas dépendre des changements d'affichage (qui expliquent le bout de terre manquant dans le screenshot là-haut), ajouté une "bbox" à l'animation (pour que le code sache qu'il ne doit manipuler que 8x8 et pas 16x16), je finis par avoir un objet qui est créé tandis que le bloc devient inactif puis se réactive ... le hic, c'est que il faut pour ça que le "corps" de Bilou soit en contact avec le bloc interactif alors que ce sont ses *mains* qui vont essayer de l'attraper. Et la zone à attraper est réduite à 8x8, de toutes façons mal positionnée... bref, je n'y arrive que 1 fois sur 5-6, donc le joueur n'y arrivera pas.
Il vaut bien mieux que je me décide à dessiner un graphisme dédié (une racine ?) et que je fasse juste un GOB dédié... il y aura des import/exports mercurial à faire ...
At some point I thought "hmm. I'll just have the little tile be a 8x8 hitbox in the middle of a 24x24 special box, that will do the trick", but it wouldn't work either: that 24x24 region around the corner of a pillar (for instance) would have "jump-through ground" on one tile, and "air" everywhere else... how could a single "props" instruction fix that ? okay, I could introduce "props(-1,0) fc4" to change one specific tile of the block but that sounds like the coding equivalent of "just stab me now" ...
So, likely, I should forget about that "hook to tile" thing, accept that there's very little hookspots in the Dreamland levels anyway and kickstart my NDS to draw some root sprite in green.spr ...