Showing posts with label water. Show all posts
Showing posts with label water. Show all posts

Tuesday, June 23, 2026

Les todos du printemps

Toujours en mode "post-desktop". Toujours avec mes carnets qui me servent entre-autres à suivre la progression (lente mais présente) du projet "dreamland". Tout le jeu, avec ce genre de carnet, c'est d'arriver à conserver facilement accessible les choses qui sont encore pertinentes. Souvent, ça passe par un coin de feuille sur lequel je vais me faire une espèce de petit index illustré des pages sur lesquelles j'ai encore des cases de "todo" à cocher ... régulièrement quand la dernière page de ce genre a perdu son statut de "priorité absolue".

Working without a desktop ... without a central unit where your project has its home and grows ... it has slowed me down for years until I opted for making the new home for my project to be made of paper instead. But that means I need to dig older contents into newer pages on a regular basis. And part of the solution for me was that this notebook hosts everything I need to keep track of.

A trick I've started using lately was to make visual/graphical table-of-contents towards past pages, in this case, all the pages where I have "TODO" items still pending, like a small mushroom getting hit by an apple to remind of the todo-state-machine that guided me through latest screenshot saturdays 

C'est évidemment la page 61 qui a ramassé le plus de cochettes ces temps-ci, avec les interactions autour de Funghi et les Applemen, au point qu'il a même eu droit à sa petite barre de progression.

D'autres points avaient été relevés lors du feuilletage et vont se retrouver grisés: ils ne sont pas utiles pour proposer une "première démo" de Dreamland. C'est le cas pour les ajouts juteux autour du poing-écrabouilleur de la pyramide. Oui, ce serait plus sympa qu'il fasse de la poussière, qu'il fasse trembler l'écran etc. mais on peut très bien tester le jeu sans rien de tout ça.

There are a good number of the other todo items that are linked to water interactions and swimming but that's no big surprise: water and swimming have been added over the previous year to an engine that was unable to handle that before, so there are plenty of little things left to tune or fix.

Once I was done with that first sweep, I tried to rationalize: I'd like to be able to let people play the game as early as I manage, and many of the todo items, while valid, aren't needed before people play. Sure, big smashing punch looks better if it triggers clouds of dust and shakes the screen as it smashes into the ground, but none of this is a blocking point if it's missing ... that's why the punch "icon" is greyed out. 

Si la page d'index visuel correspond à un moment-détente, comme certain(e)s feraient des mandalas, il y a aussi des petites notes beaucoup plus gribouillée sur des choses à corriger saisies au vol pendant que l'un ou l'autre essaye le jeu. Mon frère est particulièrement redoutable à ce numéro-là. Mettez lui un de mes programmes entre les mains et il va vous le soft-locker ou pire en moins de 2. Il aura fallu pas loin de 3 reboots pour qu'il puisse lancer une pomme sur Funghi le week-end dernier ^^".

Et comme vous pouvez le voir, c'est beaucoup autour de l'eau que j'ai pris du retard. 

And yeah, many of the items in those sub-page are less eye-candy than the index. Many of them are on-the-fly sketches of something my brother or my son or someone encountered while testing the latest version on my NintendoDS. Sometimes they are summaries of other TODO items grouped according to the tools/energy I'll need to tackle them. I can't really setup WiFi transfers through my NUC-cube while the dinner is cooking. I won't have my blog at hand to remember me what I wanted to draw on the NDS once I'll be in a no-WiFi zone with my DS around. I'd better focus on editing code once I'll be in the good setup to edit some code, etc.

Il m'arrive aussi de temps en temps de faire une version structurée différemment de ces todo-index, où je re-trie les check-box en fonction de ce qu'il va me falloir comme matériel pour avancer: la DS elle-même, le laptop, le "cube", un moment WiFi ... 

L'idée est d'essayer de mieux grappiller les moments disponibles et ne pas retomber sur "ah oui, il faudrait faire ça ... ah mais non, il faudrait d'abord que je mette à jour Bilou.cmd et je n'ai que la DS" quand j'ai une petite demie-heure qui se dégage.

Et forcément, c'est dans ces moments-là qu'arrive une idée du genre "mais oui! faire des ricochets sur l'eau avec les pommes!" ou "les chauve-souris cessent de vous pourchasser si elles rencontrent de l'eau (façon essaim d'abeilles Disney ;-) 

And of course, I have to accommodate for the fact that ideas pop up when they feel it, not when I'm in front of a nice blank page on which a big title has just been polished :P

edit: for the next week-end, analysis and preparation happened thanks to the cube serving the repository over WiFi to the boox sketchpad and then coding happened early in the morning, outdoor in the Virtual Machine of That Other Laptop (better battery, awful keyboard) through sshfs as the files and compiler were hosted on the cube too but the emulator ran within the laptop. At least, the 1st half-hour session was outdoor then the rest was coded on the "dining" table next to the coolness dispenser. That allowed me to have 3 items done (that's completing the page 61) and 2 screenshot saturday released :P      

Wednesday, March 18, 2026

Fixing unimportant things

You know you're on a hobby project when you start fixing things that are on the bottom of your priority list first because you feel ashame of their current state and there's no one pushing you to do top-priority fixes instead.

Improving the graphics of the water slide was certainly no high priority except for my eyes. Having a special "patch sprite" to allow the desired shape that needed 3 layers despite I only have 2 map layers was inevitable after that, as much as patching the color cycler to avoid half-water half-rainbow effects.

Les graphismes des pentes-à-eau présentés fin 2025 (eh oui ... déjà) avaient un truc qui ne me plaisait vraiment pas : une jonction très "carrée" entre la cascade et la pente. Un problème qui est la conséquence d'un choix dans la construction de cette cascade:

elle est constituée de deux couches de graphisme superposés. ça offre des avantages, mais ça veut dire aussi qu'à part des sprites, je ne peux rien mettre en même temps. Un problème que j'avais déjà rencontré dans le dernier niveau de SchoolRush. Problème que j'ai retourné dans tous les sens pendant les mois de janvier et février (provoqué par le même genre de problème "quelle couche ?" autour du poing écrabouilleur) avant que l'évidence ne me frappe comme un boomerang revenant de l'ère 8-bit:

rajoute un sprite.

Well, adding a sprite overlay on top of the tiles layer is hardly any innovative. In fact, it was super-common in 8-bit and 16-bit games as soon as you aimed at something visually more sophisticated than Super Mario. But no. It took me almost two months to realise that was the solution I needed here.

And took me almost as long to realise that very dark greyish stone wouldn't work in the bright-and-colorful environment of Bilou undergrounds, and that since I'd like the peaks zone to feature purple rocks, I could start introducing purple rocks as soon as the first level.

Then in a single evening, I reconstructed a draft mockup of what I wanted to see: background dirt tiles and a waterfall, then the big rock and the wavy effect (that is still to be integrated), and in a couple of hours, I repainted the rocks in a quite satisfying way.

And when I saved things, I realised I was close to 90% of tile space consumption, while there are still a good deal of things I'd like to add to the green zone. So I wrote down a note to hunt for duplicatas later and a few other higher-priority things like drawing a background screen for the underground parts... and of course, the day after, I was marking duplicate tiles and then patching them in the level maps and noting where I had alternate dirt / rock tiles that I could use to break the grid, etc. Priorities will have to wait :P

J'ai donc profité d'une soirée où ma fée était au club-créatif du coin pour aller de fil en aiguille, dessiner quelque-chose qui ne me déplaît plus, faire le montage, ajuster les scripts et rajouter le code qu'il faut pour avoir une pente qui présente bien, avant de me rendre compte que oups, je commence à avoir trop rempli ma mémoire de graphismes pour la greenzone, marquer les duplicatas, les nettoyer, etc. au point que j'ai dû retransférer presque l'intégralité du contenu graphique de la green zone (y compris les maps des niveaux) de la DS au PC alors que je vais aussi devoir faire le transfert inverse pour les scripts de comportement ^^". 

Monday, December 29, 2025

Slides testing

I've been re-drawing the water slides directly on the "three rooms" test screen, because it feels easier to prototype there than within the reconstructed green zone level. Then I've been prototyping different things about it that I had in my notes ... only mostly ruling out some options so far. For instance, the idea of re-using the sprite of waterjets to avoid issues with waterfall-to-slide transition should be forgotten ... it helped me coding something to select the layer where Gobs should appear ... one of the things I'll need for the smashing fist.

Another such test was placing some special tiles along the slide, in an attempt to make them trigger some "fall and slide on slippery ground". 

That failed. Almost completely. I had to create an empty animation just to avoid the normal "special blocks handling" from deleting chunks of the slope as soon as Bilou touched them.

I also had to drop the idea of placing "jet" tiles in an attempt to push Bilou harder out of the slope at its bottom : they allowed (but only sometimes) Bilou to hover the whole slide upwards ! 

Saturday, August 23, 2025

Une pente qui tombe à l'eau

I had tiles that push you along a slope. They've been shown in the sands mostly, but more importantly, they've been tested in a setup where there's plain ground at the bottom of the slope.

Here, I'd like to use water falling down a slope as a way to implement a one-way region somewhere in a cavern of the green zone. But it didn't quite worked as intended. What makes Bilou slide down in such a setup is that a test-point queries the tile number under his feet and use that to look up a physics values array. But once you get down the hill, the hotspot gets in the air, and nothing finishes to push you out. 

Il y a sous l'arbre creux une sorte de pente rendue glissante par une cascade sous-terraine. Mon frère l'avait utilisée pour créer une sorte de sens interdit entre deux morceaux du niveau. Alors j'ai déjà des pentes, donc ça aurait dû être une simple formalité, mais comme vous l'aurez sûrement deviné par le titre, ça n'a pas été sans mal Premier couac: en voulant rendre ce "tapis roulant" plus rapide que les chutes de sable, je suis sorti des limites d'un tableau, ce qui a eu pour effet d'appliquer l'effet geyser à l'ensemble du niveau ^^".

Plus contrariant, une fois arrivé en bas de la pente ... rien. On ne tombe pas dans l'eau, on reste juste là, sur le rebord. Parce que c'est le pixel sous le *milieu* de Bilou (le "hotspot") qui détermine si on se trouve sur un tapis roulant mais qu'il faut qu'il n'y ait plus rien sous lui sur toute sa largeur pour qu'il commence à tomber. Je dois donc rajouter un autre type de tile qui pousse comme un tapis roulant tout en étant pas du sol.

So I added another tile that behaves like air and keeps pushing you as if you were on sliding ground and put them at the bottom of the slope, but even that wasn't enough to get it working. It would take you as far away from the slope as you want, but then, once your hotspot is in plain air, you'll stop, happily idling in the middle of nowhere.

The part I was still missing was the F_START_FALLING property to my new tile type, something introduced so that we could land in slopes properly by having slope tiles letting you keep falling into them (until the hot spot reaches the ground) but not start falling through them when you're walking.

Il restait un dernier soucis. Un couac lié à un changement plus récent et qui fait qu'après avoir bien emmené Bilou au milieu de nulle-part, il ne tombe toujours pas. tout ça parce que j'ai donné au nouveau tile possède bien la propriété F_FALLTHRU, utilisée pendant que Bilou tombe, mais pas F_START_FALLING utilisée pendant que Bilou est au sol pour voir s'il pourrait tomber ^^"

With that new bit set, we finally have it: Bilou keeps sliding until there's no solid ground, and there  it cando(START_FALLING) and ends up in the water :P

There's one odd thing going on with the way the water slide is made as a conveyer, though. Conveyers just move you and don't affect your speed, and that's on purpose. But that means that as you're running full-speed against the water flow (if you manage to) and decide to jump, you suddenly move in the air at top speed while you were almost idle on the ground.

Maybe I should mimmic Sonic's water slide and make a dedicated "woah! I'm sliding down!!" state for Bilou as well.

But even then, when Bilou is walking against a conveyer, it is natural that he's walking faster than he's moving ... against water, we all know there's a force slowing us down, so it'd make sense to see his animation slowed down and pixel-fitting its motion against the water ... which would mean acting on his speed rather than shifting his position ... Meditate on this I will. 

Saturday, July 12, 2025

Mario in Godot

Refaire Super Mario World dans le game-maker "Godot" ... j'ai envie de dire à la fois "tout ça" et "rien que ça". Pourtant, l'idée de Wye n'est ni de proposer un Mario World Studio ni son Mario World 3. L'idée, c'est de comprendre le fonctionnement du jeu d'origine en le reconstruisant dans un nouvel outil tout en apprenant l'outil lui-même. Et ça, ça me parle. C'est le genre de bouquin que je dévorerais mais ici, ce sont des vidéos youtube.

"In Super Mario World, Mario was considered fully underwater if both his head and body interaction points are touching water tiles. [...]

That's the kind of things you can learn by watching Wye's series on re-making Super Mario World in Godot, and learn how to use Godot in the process

I've been following the videos roughly since episode 1 or 2, but as Wye now address the water physics, I cannot just remain a silent watcher. I've spent too much time working on water physics myself, and I need to compare the approaches. Of course, Mario isn't using the "cando"  function. Instead, interaction with the world are guided by "interaction points" which remember the type of tile they're on. So for instance, 

"When Mario body is in the water but not his head, that means he is near the surface."

Du point de vue des collisions avec le niveau, Mario n'est pas une boîte. Il est ... une sorte de constellation de points qui ont chacun leur préférence sur le type de terrain 8 en tout, mais dont certains ne seront évalués que dans certaines conditions. Pour déterminer s'il faut nager ou non, ce sont par exemple ce sont les tests du milieu et de la tête qui entrent en ligne de compte. Et pour déterminer si on peut sauter hors de l'eau ? Bin il faut que le corps de Mario soit dans l'eau mais sa tête hors de l'eau. On évite en fait les complications du type "la surface est à la fois de l'air et de l'eau" dans lesquelles je me suis embarqué.

And only when Mario is near the surface is it possible to jump out of water ... and only if pressing UP in addition to pressing the JUMP button ...

The concept of interaction points comes from the disassembly of SMW itself and was discussed in an earlier video. They replace hitboxes when it comes to interacting with the world and there are 8 of them for Mario. But as usual with 16-bit games, not all points are tested on every frame. What is interesting is that rather than testing e.g. "left side" when moving left, the game tests "left side" only if the left side is "smaller" than the right side, as a way to detect "new" things, assuming that what covers most of Mario's box has been tested in the past. "When Mario is on the right side of a tile, the two points on the left are ignored" is possibly a better way to describe what happens, indeed ^^".

I'd be curious to find out to what extent that keeps working where your level grid isn't exactly one hero wide ...

edit: while you need to *press* the jump button to make Mario jump when he hits the ground from a fall, you just need to be *holding the button down* when reaching the water surface to trigger "jump out of water".  (from the "extra bits")

Wednesday, April 30, 2025

Puddlehead splash

There's one thing I still miss in my water implementation, and that is splashes. The most beautiful waterfall will fall flat if the water pool doesn't acknowledge you've changed physics by a nice splash of pixels.

I've gathered a few references in my pixelstudies, and this one comes from
puddlehead-creations.itch.io
The video was initially intended to demonstrate how surfaces in GameMaker can be used for palette-lighting  in CinderHoodGame, but what caught my attention was those simple an efficient splashes, which I wanted to pixelstudy.

Un beau splash! Voilà ce qu'il manque à mon petit coin aquatique... Et des beaux splash, vous pensez bien que j'en ai croisé 2 ou 3 depuis que j'ai dessiné la cascade. Celui que vous voyez ici apparaît avec l'autorisation de Puddlehead Creationset a été patiemment extrait à l'aide de VLC d'une vidéo présentant un nouveau shader pour leur jeu CinderHoodGame

As often, such material is posted as a video, so I had to frame skip to get the different steps studyable. May I  call this family of splashes "noisy gaussians" ?

There are two separate animations, depending on whether you splash into the water pool or out of it. 

In both case, I'd first animate the big white part and only then add those noisy spikes and make them turn into "independent droplets" as the splash collapses.

Ne pas hésiter à faire deux animations, une pour "plouf dans l'eau" et une pour "sphlash hors de l'eau" ... partir d'une courbe en cloche d'écume blanche, ajouter des déviations pour le haut ... attendre le moment où l'eau retombe pour ajouter des goutelettes qui suivent leur chemin ... voilà ... à tester.

En comparaison, l'eau de Super Mario World fait un peu pitié ... une couleur unie, une surface statique, un splash qui recycle le nuage de poussière, selon moi ... Par contre, je note l'idée intéressante de faire apparaître au moment du splash des petites bulles qui remonteront à la surface ;)

In comparison, SMW's water is very cheap, with static line, solid blue, unconvincing splash recycling dust sprite ... but it had the good idea of spawning bubbles under you. Rayman's sprite is beautiful, but low framerate and oversized for Bilou's weight. Fury of the furries reused their particles engine but imho could use some fine-tuning... And Hydrocity used something too blast-ish.

edit: One more splashy video posted by Puddlehead creations, just in time to replace the one I used for the snapshots ^_^

Tuesday, April 15, 2025

gravity.flow ?

Je voulais faire tout autre chose, mais au moment de prendre le code en main, je me rends compte que j'ai une série de modifications qui n'ont pas encore eu droit à leur commit ... et que je ne sais plus trop à quoi elles correspondent.

Il s'agissait en réalité de deux modifications liées à l'eau: animer la surface (nager si bien avec un miroir en guise de surface, c'est un peu dommage ...) et faire en sorte qu'on puisse placer un jet d'eau dans une grotte. Parce que vous ne ça n'aura pas manqué de vous faire tiquer: il y a une sorte de rectangle moche au pied du geyser sur l'image ci-contre/dessus. C'est lié au fait que le geyser (tout comme la cascade) est obtenu en par une combinaison des deux couches de décor: l'une avec une animation de type "palette cycling" et l'autre avec une animation conventionnelle. Et donc pour mettre le geyser dans une grotte, il me faut deux nouveaux blocs "décor de geyser fusionné avec le décor de grotte".

After a fairly busy week and significantly busy Saturday, I wanted to try updating the Appleman behaviour, but I found my homebrew directory with different files uncommitted and changes involving binary files like maps. So I started by running the current code first on the emulator, and visit those maps to see whether there were any changes. And oh, of course. First change was animating the water line (see the mastodon video below). Second was an extra water jet in the second green map.

Quand je dis "je ne sais plus à quoi elles correspondent" (y compris une modification du code qui assure le palette cycling), comprenez "il a fallu que je fasse tourner le .nds pour m'en souvenir". Ce qui m'a donné envie d'en faire des petites captures (un jour après le ScreenshotSaturday ... pas de chance ^^"), et sur une de ces captures, on remarquait quand-même fort que le haut du geyser reste en permanence au même emplacement. Moi, j'aimerais qu'il monte et qu'il descende, pour ajouter un peu de dynamisme à la scène, et appeler à l'interaction.

See on that level editor, waterfalls and geysers are made of two layers of tiles combined. But that means you can't put a geyser over a dirt wall unless you've got tiles showing that in first place. Plus I'm using another palette slot for the dirt wall than the default one, meaning the cycling code had to be updated. That was ready for some screen-shotting

J'aurais peut-être pu utiliser le contrôleur "grid" de furblock, mais tôt ou tard, il faudra aussi que Bilou soit propulsé vers le haut par le geyser. Plan B: utiliser le même mécanisme de "flow" dans le contrôleur gravity que celui codé pour swim. Je profite donc que tout le setup wifi est là pour modifier le niveau et je définis un nouveau type de tile (les ^ mauves). ça donne des résultats rigolos avec Bilou, mais en réalité, ça ne marche pas: Bilou est bien ralenti quand il arrive dans le haut du geyser, il peut même remonter légèrement, mais au final, la gravité lui donne une vitesse suffisamment élevée (on peut aller jusqu'à 6px/frame) pour qu'il redescende, puisque le geyser le fait monter à une vitesse constante de 2px/frame. Bref, c'est bien pour des tapis roulants mais pas pour des geysers.

But then, the top of the geyser was very static ... I want it to wave up and down a bit. There are different ways I could do that in my engine, but only a few where not only the geyser top but also Bilou is lifted up when in contact with the stream. That implies a mechanism similar to the water flow designed last year, except this new special physics tile will define a property for the gravity controller instead. It will still be an "AIR" tile, though: we can fall through geyser, not swim them. (I hope to avoid nasty corner cases that way).

Unfortunately it didn't work the way I wanted. Lifting Bilou by 2 pixels (cyan lines on the diff) is fine as long as the vertical speed is lower than 2 pixels/frame downwards. It gives a nice boost when jumping and catches you when you're "stomping" the geyser, but while you're being stopped, your intended velocity keeps increasing, and at some point, you'll be fast enough to reach the ground again. Exactly as you start sprinting backwards on a conveyor belt.

So I ended up using the yellow code instead: directly change the polarity of the gravity based on the sign of the terminal velocity stored as a per-tile-type property. Not perfect, but close enough for now.

Mais en fait, il n'y a pas tant à changer que ça: plutôt que de déplacer Bilou, on va utiliser l'information stockée pour contraindre la vitesse maximale ... et tant qu'à faire, inverser la poussée si la vitesse maximale est négative. J'ai pris des vitesse identiques pour la gravité et le jet d'eau pour le "petit nuage" en haut du geyser, ce qui lui donne un mouvement symétrique alors que pour Bilou, la gravité lui permet d'acquérir une vitesse jusqu'à 3 fois plus grande, et il a donc tendance à s'enfoncer plus dans le jet d'eau. ça suffira pour le premier jet ;-)

edit: valeur maximale -2px/frame validée: il suffit de garder le bouton de saut enfoncé pour décoller bien au-dessus du geyser. Et si on tombe du sommet, on ne redescend pas trop bas.
 

Post by @PypeBros@mastodon.social
View on Mastodon

Monday, February 17, 2025

pixels, at last.

Une petite heure de week-end où j'ai pris le temps de me faire des petits pixels ... enfin. Après une autre petite heure plus tôt dans le week-end pour faire quelques essais de croquis.

L'écrabouilleur, d'abord, qui est la résultante de mes esquisses basées sur Ristar, des techniques proposées par Helm que j'avais utilisées pour les livres de l'école et de la réalisation que  finalement, des gants façon Mickey donneraient sans doute mieux dans l'univers de Bilou que ma propre main.

Il se trouve que j'avais déjà tenté de dessiner ma main, et j'avais la S-Team en entier et le verdict est sans appel: le nouveu design, plus anguleux, s'intègre mieux.

Finally, I managed to find 2 hours to work on the missing pixels I need for Bilou's demo. First the smasher punch, using all the observations I made while posting about my Ristar pixel study. It's more squarish (and the S-Team girls like it), it has cartoony-4-fingers look and is modeled after a cartoony glove rather than my own hand. Quite close to the sketch I made the day before. I'm still undecided about the thumb position ...

Second, the top-of-waterjet sprite. I won't try to make a tutorial of how-to-animate it: there is very likely room for improvement, but it does a fair enough job (imho) and nicely fits the style of the jet (see below for the in-game montage ;). I'll still have to make it wave up and down and make it so that the jet pushes Bilou upstream on contact.

Deuxième morceau: le haut du geyser inspiré de GoodboyGalaxy. Il faut dire que les derniers tests se déroulaient sur une map où j'ai ajouté l'animation pour la partie verticale du jet ... et bon, voir le jet se terminer par une ligne nette comme ça, ... ça picotte aux yeux.

Je ne suis pas franchement au niveau de hot_pengu, mais je crois que ça devrait faire l'affaire malgré tout (NB, c'est plus fluide en vrai sur la DS).

Saturday, January 18, 2025

Hydrocity pixel waterjets

Bin ça! Il y avait un parfait exemple de jet d'eau dans un jeu 16-bit dans la série Sonic, et j'étais complètement passé à côté! Heureusement qu'il y avait Tim pour poster une photo de son Anbernic Arc-S pour me remettre sur le droit chemin!

L'effet est plutôt convainquant, plutôt utilisé comme script de transition/narration entre 2 phases que véritablement comme un élément de gameplay interactif, mais ça reste pertinent. Il reste un peu moins de 2 secondes à l'écran avant que Sonic ne soit propulsé plus haut tandis que le jet redescend et sort du cadre.

Last year, I was looking for 16-bit references of a water jet and I couldn't find anything satisfying, but it seems like I completely missed those location-transition-events in Hydrocity Zone act 1 of Sonic 3. I hope you'll excuse me: my memories of Hydrocity essentially resume to "this place hates me". Trying to keep enough air in Labyrinth Zone wasn't easy, but it felt possible and a sort of appropriate final challenge in the game. You'll completely miss the water jets if you're watching a speedrun or any competent player as well: they're sole purpose is to bring back upwards player who failed to stay on the high dry path.

ça se passe dans Hydrocity, la deuxième et parfaitement imbuvable zone de Sonic 3. Il se trouve que j'ai le jeu sur une cartouche combo Sonic Genesis 2D pour NDS et j'ai donc fait l'effort de retourner jusque dans Hydrocity, mais sans encore arriver jusqu'au jet vertical pour me rendre compte par moi-même.

Il faudra pour ça, une fois le jet horizontal passé, que je m'aventure dans les profondeurs jusqu'au couloir avec les hélices qui nous poussent vers la droite. ça malgré les pics, les poissons mal foutu et les tapis qui nous ramènent en arrière juste quand on est sur le point de pouvoir reprendre de l'air ... C'est beau le rétro, mais là, c'est quand même pas loin de l'abus vu qu'on est encore qu'au 3eme stage du jeu ... 

For the era, they seem to work surprisingly well. They only need 4-colors palette cycling, and are even somewhat light on tiles consumption, with a 32x32 pixels pattern (plus mirroring) for the trunk and 32x48 for the top (and even one 16x16 block of the top being shared with the trunk). You've got one big arc per pattern, which clearly works better than the repeated pattern of Mc Donald's Treasure Land Adventure. (although, this is not the worst water animation in that game ...). Note too how the top part uses the raster in opposite direction so that it feels that water is falling down there. (yeah, obvious, I know)

Bon, mais trève de rouspétances, regardons ces pixels. l'artiste s'est concentré sur un motif d'arc répété avec un dégradé plein de tramage (plutôt une bonne idée sur la technologie CRT de l'époque) pour finir par un arc de cercle plus arrondi où le dégradé est mis à contre-sens.

Le tout est évidemment animé par palette cycling ... ça vaut mieux vu la surface à prendre en compte. A noter aussi la grandeur du motif. On a pas essayé ici de faire de petites vagues répétées: la partie "champignon" est constituée d'un seul dégradé ! Du coup, c'est bien l'effet "mouvement" qui prévaut sur l'effet "clignottement".

The pattern is rather noisy, but that shouldn't be a big issue for the CRT screens it is designed to. Given the size of each area, the motion illusion prevails over the flashiness. At least when played at 75% of the intended 60fps. Maybe it also worked at 60fps on CRT screens (we had 50Hz here, so who knows ...). 

All I can tell you is that it took me dedication to bring Sonic in the proper spot(s) of Hydrocity on my Sega collection for Nintendo DS cartridge and on the 3DS LCD screen the result was ... meh ... mostly getting a averaged blue tint all over the jet, the pixels staying in place for most of the 2 seconds where we see the jet, with my brain saying "ah! I spot the pattern!" rather than "wah! That's blasting fast!".

So well, it was a nice reference at the time. I mostly works because you're taken off-screen once the jet should retract and because it's a one-time event rather than what I need (a trigger-on-demand event) or what Mc Donalds and Bubsy games needed: an platform going up and down continuously.

J'affronte donc une deuxième fois le niveau, fort de la carte mémorisée ... il y a surtout des zig-zag imposés à toute allure entre les deux jets d'eau du niveau 1 (aucun dans le niveau 2, qui a besoin de ces tiles-là pour nous mettre plus de toboggans). Je peste contre les poissons-pirhaña qui m'empêchent de sauter pendant plusieurs secondes alors que les bulles d'air ne sont suffisamment grande pour respirer qu'à partir d'un sonic du sol ... je choppe un bouclier-bulle ... je le perd ... je suis propulsé une 2eme fois.

Eh bin, les gars, l'effet "mouvement", à 60fps sur un écran LCD, il est un peu perdu dans la bagarre ... on voit juste une trombe bleue d'une couleur plus ou moins uniforme tellement ça va vite. Un peu déçu, je vous l'avoue.

Saturday, January 11, 2025

Cosmic Boll by Yoritoshi

There was a twitter account I held for later while leaving the network: it had a yellow ball avatar, and I remembered a few nice exchanges with somebody doing a platformer featuring a yellow ball, but I couldn't find any track of those exchanges. I ran out of keywords idea to grep my tweet.js and blog.xml ... I asked my contacts for help, but I still wouldn't find it.

cosmicboll animated screenshot showing waterfall pushing you down
But eventually, in the "more tweets" online document I've been crafting, I found back the picture I wanted, where cosmicboll (and not bowl or ball) encounters a waterfall and the water pushes it (him?) down, increasing gravity. Something I don't have yet for my own waterfall and that definitely looks and feel fun.

The game is not from that person with the yellow ball avatar but from the Spanish-speaking developer Yoritoshi, who has been working on the game since at least 2018.

The small snippet I have here may give you the feeling that there is some Sonic legacy in that title, and likely Yoritoshi's videos will convince you even further, since some of the sound effects featured are raw samples from the megadrive titles.

Petit résumé pour mes lecteurs francophones: La balle jaune dans le gif animé ci-dessus est le personnage principal du jeu "cosmic boll" de Yoritoshi, dont j'ai suivi de loin le développement au fil des tweets. On aurait presque pu appeler le jeu cosmic Brawl, vu l'importance que les combos et la variété des attaques dans ce qui aurait pu aussi non passer pour un Sonic-like. Le jeu est téléchargeable en version Windows sur le site itch.io du dévelopeur et je n'y ai pas encore joué.

Avant les premiers tweets présentant ce jeu-là, l'auteur travaillait sur des fangames Sonic, bien intégré dans la communauté, étendant le travail d'un certain "LakeFeperd" et participant à la convention SAGE régulièrement.

It is even stronger when you get a look at the level editor screenshots that Yoritoshi published: there are ramps, there are loops and all ... There are some explanation in the earliest tweet using the #cosmicboll tag:

Began to add enemy characters of my own to replace the dummy from LakeFeperd's engine with, but I hope CF2.5 doesn't pull any nonsense on me when I add hitboxes to their attacks. (Jan 20, 2018)

LakeFeperd's own video often mentions SAGE event, and if we dig deeper than the video about "Spark the Jester", we see that they are about Sonic fan games... So yeah, people gather to show each other their Sonic fan games (and likely fanart and play sonic games and plenty of blue things), there are Sonic-targetted game engines for many different game construction kits, and Yoritoshi was already doing that in 2012.

But Cosmic Boll is not just a Sonic clone. Actually, the gameplay does not feel that much like Sonic. The amount of attacks you have at your disposal to dispatch foes is just impressive. If you believed "Kirby Fighter mode" has a large range of attack, Cosmic likely features 2 or 3 times as much moves. The amount of enemies per wave and the hitpoints per enemy is clearly designed to make the fights a key moment of the game and feel overpowered. And then there are "orbs" you can collect which will e.g let you turn into a fireball when you dash or shoot firewaves when you punch.

And there apparently also are special gadgets that allows you to make surprizing things like sizing down ennemies, althought I have to admit I haven't understood everything about that.

Saturday, July 06, 2024

Test tile type from state transition

As I update an old post to explain that yes, cando() finally managed air/water transition I note that the whole blog is still missing a key explanation of how this was made possible. It happens in state machine transition expression (in the predicates, actually) and says "tell me the properties of the world n pixels above my hotspot".

$FALL->$INWATER on fail [2 H WATER ?]
                        (v1 v5 + 2 / :1 0 :5);

$INWATER->$RBOUNCE on event0 [D_FOOT 8 H AIR ? &]
                        (800 ~ :1);

You see it there. H is the new OP_HOTTILE for the GobExpressions. it picks the value on top of the stack, the constant 2 or 8 here. We can then test bits against the constants WATER or AIR with the ? operator.

Without that, the trick about a slice of tiles that are both water and air is useless, because you couldn't make the difference between falling into water and falling on the ground anyway.

(and yeah, I still have to add those get-worldwide-flag and set-worldwide-flag opcodes as well as the roll-the-dice opcode)

Saturday, May 04, 2024

Goodboy('s geyser) was here

J'ai quand-même commencé à tenter de dessiner un jet d'eau. J'avais lancé un appel sur twitter, pour essayer de trouver des références. Il faut dire que les cascades de l'époque 16-bit étaient encore plus convainquantes que les jets d'eau de la même période.

J'ai eu une réponse en or, du genre de celles que j'ai eues pour les arbres l'an dernier. Le temps de faire le point, et je vous raconte tout ça ;)

"I can't draw convincing water jet from below" did not sound like a very convincing reason for not using a water jet if it is the proper game mechanic to use. I finally have a good one to pixel study and started doing my own, as you can see on the photo, but allow me to rewind and start where it started.

Un pas en arrière pour revenir à l'époque 16-bit. On préférait souvent éviter d'avoir de trop grosses animations à gérer sur ce genre de machine, et animer de l'eau se faisait généralement avec un dégradé et une modification cyclique sur la palette de couleur (palette cycling). Le foncé devient blanc pendant que le clair devient foncé, le très clair devient clair et le blanc devient très clair...

Back in the 16-bit era, it was frequent to do color cycling to animate a waterfall. Sometimes it worked nicely, sometimes it was so-so. It works best if the raster is long enough and if the animation speed remains movie-quality. At cartoon-12fps, you start seeing as flashing more than falling down water.

But you'll note the bottom of the waterfall is often missing in those scenes. And when you look at the few game art that tried having upwards water jet, you understand why: it no longer works. We expect water to become darker with density increase. In a waterfall, vertical density variation are interpreted as downwards waves, but when water eventually widens up in a fountain-like mushroom cap, it is always more dense at the center and less dense on the "edges". If you do palette-cycling here, you break that.

ça donne une illusion potable de cascade, pourvu qu'elle ne soit pas trop grande et que la vitesse d'animation soit réglée au millipoil. Et si possible, utilisez plus que 4 couleurs pour le cycle, parce que sinon on se retrouve avec quelque-chose comme le décor de Yoshi's Island qui tient plus du clignotement que de l'écoulement d'eau. 

Et malheureusement, la même stratégie est appliquée dans les (nettement plus) rares jets d'eau de l'époque. Je dis "malheureusement" parce que pour un jet d'eau, on va forcément devoir aussi animer le "chapeau de champignon" qui va avec, pour lequel la surface animée est encore plus grande. Et l'effet clignotement encore amplifié. On l'a déjà dans Bubsy, où les pixels isolés clignotants ne parviendront pas à faire oublier le fait qu'ils sont statiques. On l'a dans le final de Link's Awakening et dans le jet d'eau d'un jeu obscur avec la mascotte du Mac Do.

In Bubsy, for instance, the artist sprayed out the water pixels as the water starts falling down. This is coherent with the style, but animating them will just give you blinking static pixels of water. And the stylized 'mushroom cap' used in Link's Awakening and Mac Do game flashes even more aggressively.

Là où ça coince tout particulièrement avec le "champignon", même quand on évite les pixels statiques, c'est qu'avec ce type d'image, le clair et le foncé ne sont plus interchangeables. On voudrait que le bord soit plus clair parce que l'eau y est plus éparpillée. Faites-y du palette-cycling et vous aurez des images qui donnent l'impression d'être en négatif.

J'avoue que je trouve un peu dommage qu'avec les resources graphiques de la SNES, on en soit réduit à ça pour animer l'eau. Mais il faut reconnaître qu'en misant tout sur de la RAM vidéo, la console n'a plus la possibilité de reprogrammer les plages d'adresses (bank switching) pour faire des "animations gratuites" comme la génération 8-bit. Toute animation va impliquer un transfert DMA vers cette VRAM et le budget pour ces transferts est limité (comme toujours).

Truly, the "cap" of the fountain/geyser needs dedicated animated tiles, but we're unlikely to see that on 16-bit engines. 8-bit machines could have done that with more ROM and evolved mapper chip, but 16-bit consoles no longer try to pull pixels directly from the ROM. They put them in dedicated video RAM, and rely on DMA channels to bring animation frames in due time. But the amount of pixels you can transfer per frame is limited. Animating Bubsy's geyser that way at 60fps would consume 25% of your animation power:

On NTSC with overscan mode turned off, there are 262 - 224 = 38 scanlines in vblank. Subtract one scanline for prerender time, and you may end up with 165.5 * 37 = a smidge under 6 KiB per vblank.

6K, sur SNES, c'est 46 blocs-question de Super Mario World. Animer quelque-chose de la taille de la fontaine de Bubsy à 60fps, ça demanderait donc 1/4 de la puissance dans la partie critique du moteur de jeu.

Bon, et après l'époque 16-bit, alors ? Du côté de Super Princess Peach, par exemple, qui est plutôt réussi côté pixel art ? Un jeu ou pleurer est une mécanique de jeu, il doit bien y avoir des jets d'eau dedans non ? 

So, well, my game is not for a 16-bit system anyway, so could there be any water jet pixel art for 32+ game that I could study instead ? Say, in Super Princess Peach ? A game where you cry waterjets sure should also have some geyser-like elements, right ?

Well, it does indeed, in Wavy Beach 2. It uses a "cone" of water that might be animated through color cycling plus a "flower" top that follows the rule "keep the center dark and the edges light". But even then, I don't find it appealing, and I don't see how I could make it match anything but the super-stylized environment of SPP.

Eh bien oui, en effet. Dans le niveau 2 de la plage. Mais je dois bien avouer que je ne suis que moyennement emballé par le style. On a un premier élément (le cône) qui utilise un effet de palette qui ne fonctionne pas trop mal, les traîts latéraux restant sombres en permanence. Puis on a cette "fleur" qui grandit et rétrécit, gardant toujours le sombre au centre et se permettant des éclaboussures au bord des "pétales" sur la dernière frame.

Mais ... bof. Même en corrigeant le truc pour que la princesse apparaisse par-devant la fleur, ça ne me convainc pas. Oh, ça marche plutôt bien avec le reste de l'esthétique stylisée de SPP, mais ce type d'animation dans Bilou ? Pas convaincu.

Et depuis ? Parce que bon, le modèle pour la cascade de Bilou, il ne date pas de 2005. Mais le truc, c'est que j'ai surveillé les cascades en pixel art pendant pas mal d'année, sachant que j'en aurais besoin tôt ou tard. Alors que des geysers, c'est plutôt un truc de dernière minute.

Et c'est là que hot_pengu, l'auteur de Goodboy Galaxy, m'a pointé vers la vidéo de son jeu sur GBA

And so I finally asked hints to people on twitter who might have seen something I could use as a reference, or ever proper keywords to search for one, and to my surprise, I received an answer from indie game developer hot_pengu:

We call it a 'geyser' internally for goodboy, and this (timestamped vid) is how we represent it.

Je jette un oeil, je prends un petit screenshot pas fou mais qui pourrait donner un point de départ, et là,

Here's a better look, if it's useful! (there's two versions, one comes out of a monster)

He added as I posted a quick snapshot for future pixel study, handing the Goodboy Galaxy spritesheet with 2 sizes of exactly-what-I-needed material that you see printed on the top photo. 6-frame stunning animations, with tileable base and stylish top. Even the style isn't that different from the one I have for my waterfall!

Une animation pixel-art moderne, tout en fluidité et utilisant bien les 6 frames, qui peut être étirée en hauteur comme on veut ! C'est celle que vous avez vu tout en haut de cet article, imprimée et que je suis occupé à étudier. Parce que là, j'ai bien mieux qu'une référence pour donner une seconde chance au cas du bouchon: j'ai une idée.

Voyez, ce geyser, je peux le placer au fond du trou, directement, sans avoir besoin de bouchon. Il bouge, il attire l'attention. Pas moyen que le joueur ignore sa présence. Il a un look quelque-part entre la plate-forme et le bumper ... on pourrait toujours sauter dessus, on ne sait jamais. 

I like how it simply requires the player to hop into the proper spot to trigger. Much cleaner gameplay than the "pull the cover" I had thought about, but it remains interactive. Plus, by being already flowing before we interact, there's no more questions about "where does this water comes from, where does it goes afterwards", etc.

Deuxième bon point, une fois que Bilou a sauté dessus, je peux réutiliser le type de comportement que le joueur rencontrera plus tard avec Inkjet: Bilou reste "coincé", la pression s'accumule et wouf! on est projeté vers le haut.

And that would match the way 'inkjet' monsters will lately be used as delayed bumpers in the School Zone ... Since this game will no longer feature a welcome screen with the inkjet, it's a good thing the player can be shown early what happens after the "caught in a boiling pot" animation.

Et si il a raté son premier saut, il peut retomber sur le "chapeau" du geyser et re-sauter de là.

Mieux encore: si le joueur n'est pas resté dans le geyser jusqu'à être projeté, on peut le pousser vers le haut s'il entre en contact avec le "pied" du geyser. Et si rien de tout ça ne se produit, on peut directement réessayer la même manipulation. Pas de risque d'aller se coincer en nageant, de faire redescendre l'eau trop tôt ou quoi que ce soit de ce genre.

Bref, j'avais pensé vous redessiner *mon* geyser sur DS pendant la petite semaine de vacances, mais au final, j'ai juste eu le temps de faire une petite feuille de notes pour illustrer ce que j'imagine comme mécanique avec mon geyser ... parce que les vacances d'une famille 11 + 15, ça ne ressemble pas vraiment à la dynamique 8 + 12 et ses plaines de jeu à surveiller :-P

I expect that the platform-look of the geyser top will invite even the younger players to jump on. I expect that its animation will catch their attention much more than a purple block or handle. Should they fail to use the bump effect to reach the key, they can be caught by the platform-top and jump again. If they jumped out before the geyser happened, they can jump into the flowing geyser and be pushed up to the platform-top. It's flawless ^_^

Now I just need to find enough time in the upcoming evenings to complete it ^^"

PS: if you want to animate something like that, consider animating it without the vertical motion first: just the wobbles and the sparkles, and only then apply the vertical shift to each frame. Unsure I will follow that advice myself this time.

Wednesday, April 24, 2024

'faut pas pousser!

Vous êtes devant une porte verrouillée au fond d'un tunnel. Il y a un trou rempli d'eau sur le chemin menant à la porte, alimentée par une chute venant de la galerie supérieure. Votre sens de l'exploration vous sussure que la clé pour la porte doit se trouver dans une des galleries supérieures que vous avez aperçues durant votre chute. Vous pouvez sauter avec (A) et ramasser des objets moins lourds que vous avec (B), mais la galerie supérieure est trop haute pour que vous puissiez l'atteindre en sautant.

Bon, vous l'aurez compris, je suis à la recherche d'une alternative pour le niveau 1-1 de Bilou qui ne dépende pas d'une action a priori peu maîtrisée à ce stade comme "pousser un bloc". Mais j'ai quand-même envie que le joueur ait la sensation de s'être tiré d'affaire, pas juste d'avoir fait demi-tour.

Ayant tout juste rejoué à DK Tropical Freeze, ma première idée était de mettre un gros bouchon au sol et de le retirer avec (B). Si il faut, on pourrait même faire en sorte que le bouchon dépasse un peu et qu'il laisse passer une goutte de temps en temps, pour attirer l'attention du joueur. Sauf que ... dessiner un geyser, c'est plus facile au bic qu'en 256 couleurs ... l'animer, c'est plus facile dans la tête du lecteur qu'à l'écran... Et ce n'est pas l'époque 16-bit qui va m'aider, cette fois-ci. >_<

How do you get yourself out of a hole when all you can do is JUMP and GRAB but you cannot jump high enough ?Maybe you're lucky and there's a plug-like think holding water that was just waiting for you to spring out. That would save me the trouble of needing to code raising water level and making the player confident that they won't drown if they fill the room with water ... But I have no idea how I could make a convincing geyser and '90s pixel art really does not help this time.

A supposer même que je trouve des graphismes concluants, et si le geyser a l'avantage de ne pas demander de jouer dès le niveau 1 avec de l'eau qui change de niveau, il reste un problème physique: il faudra que je trouve un layout qui explique que l'eau du geyser monte alors que l'eau du "puits" non.

Est-ce qu'on pourrait s'en sortir avec le bouton de saut ? C'est quand-même la mécanique de jeu n°1 ... On pourrait donner un coup de tête dans un truc ou tomber sur un machin qui ferait apparaître des plate-formes (disons des feuilles depuis des lianes, pour rester dans le thème de la forêt) puis sauter de feuille en feuille pour se tirer d'affaire.

Mais j'ai le même soucis qu'avec les Ethers en 200x: c'est un comportement de sale garnement et je voudrais que Bilou reste un personnage exemplaire (malgré son caractère ronchon). (De nouveau, le lecteur attentif sentira l'influence de DKTF et de ses plate-formes rangées contre le mur qu'il faut faire basculer à l'horizontale ... mais dans l'autre sens)

Could there be anything that would trigger a useful event if jumped on ? Like making buds bloom into leaves large and strong enouh to be used as a platform. But unfortunately the only such trigger I could think of imply that Bilou is hurting the target and that pain is the thing that forces blooming. I'd rather not have Bilou do such things if I can avoid it.

Par contre, l'avantage de cette idée, c'est que comme j'ai l'intention de permettre à Bilou de s'accrocher en appuyant sur (B) en l'air, on peut remonter soit en combinant attraper/sauter, ou en utilisant le "mécanisme" pour faire apparaître les feuilles. (détail sans importance puisque le joueur un poil rôdé au jeu n'aura pas oublié d'aller chercher la clé en premier)

Mais sinon, il y a une alternative plus sympa, inspirée du "dragronce":

Dans un recoin obscur, vous remarquez une sorte de tête, mi-crocodile, mi-végétale inconsciente et a l'aspect desseché. Vous faites immédiatement le rapprochement entre la texture de son "cou" et celle des lianes qui sortent ça et là de la paroi

 But maybe there could be something that can be grabbed and carried around to produce the same effect. Like the head of a thirsty dragonthorn, since there's water just nextdoor. That would be nice from Bilou to bring them into water. Might be a bit tricky to draw too ... even with pencils, I'm not convinced by those sketches... and it's a bit ... convoluted.

On peut ramasser sa tête comme les autres objets... on peut l'amener jusqu'au point d'eau pour qu'il reprenne des force et que ses feuilles se changent en plate-formes. La bonne nouvelle c'est que ça fonctionne même si le joueur n'a pas encore compris que B=ramasser et pas B=frapper.

Et avec le saut comme mécanique, est-ce qu'il n'y a pas moyen de faire quelque-chose qui soit sympatique ? Disons qu'il y ait une grosse racine qui soit juste un poil trop haut pour profiter de toute cette eau pour grandir, hein ? il suffirait de lui tomber dessus pour l'enfoncer un peu, elle se réveille, elle boit, les feuilles repoussent. C'est simple, c'est visuel, c'est le bon plan. Non ? 

'bin pas forcément si j'en crois mon frangin... lui, en tous cas, il n'a pas franchement accroché à cette approche.

Or maybe there could be something that wouldn't mind being jumped on and yet make the leaves bloom? Like a big fat root just about to reach water? It would actually be friendly and helpful to push it into the water just enough so that it could come back to life, bloom, etc. Well, I thought I had the perfect solution here until my brother seemed unconvinced.

Bon, qu'est-ce qu'il me reste ? En fait, dans le design d'origine, il n'y a même pas ce genre d'ascenseur interactif à mettre en marche. Le frangin, il avait dessiné un tuyau, une chute d'eau alors qu'on est déjà un demi-écran en dessous de la galerie supérieure, une pente-qui-pousse avec l'eau qui dévale et qui nous entraine jusqu'au bassin Est.

Celui qui n'a pas la clé n'avait qu'à penser à aller dans l'eau et prendre le téléporteur si tant est qu'on ait de l'air jusque là ... ou mourir et recommencer.

That brought me back to the original level design from my brother, only to realise that there was just nothing to help you climb back and get the key you need. Actually, he did even put one-way-watery-slope (inspired by Sonic's Labyrinth zone ?) to push the player into dive-or-door decision. If you dive, you'd have had limited time to locate the teleporting device that brings you back overworld where you could try a better route and find that key.

I don't think it could be used as-is in a modern game (and I want Bilou's Dreamland to feel modern) but since I now have waterflow tiles, I could definitely have some spot reachable from the water surface (Bilou can't dive freely in this game) where you're swallowed by a stream bringing you back where the teleporter would have dropped you. I think I'll have that anyway. But not just that. 

Pendant tout un temps, pour la reprise du niveau, c'était hors de question parce que mourir, c'est has been et que l'eau nous fait flotter, pas couler, donc pas question d'aller explorer le fond des choses avant d'avoir débloquer le bon pouvoir (metroïdvania avant l'heure).

Mais là, maitenant, j'ai des blocs qui permettent d'envoyer le joueur à travers un courant forcé ... je peux donc prévoir qu'une petite partie de ce bassin serve de départ pour une trajectoire "remontante" vers l'emplacement prévu pour la sortie du téléporteur "ah ouais. Comme dans Bubsy" ajoute mon frère.. visiblement, cette stratégie-là, ça lui parle. Je tâcherai donc de la mettre dedans, mais j'aimerais quand-même avoir une alternative plus directe pour le joueur qui a envie de trouver la "solution" plutôt que de contourner le problème.