Wednesday, July 29, 2009

powersave

Jusqu'ici, mes petits programmes étaient plutôt dévoreurs de batterie sur la DS. J'avais beau dire à mes p'tits n'veux que "tu fermes ta DS et tu viens manger tes frites, le jeu sera toujours là quand tu auras fini", c'était loin d'être le cas pour Bilou ou mon sprite editor.

Et pourtant, le fonctionnement est plutôt simple: un registre (REG_POWERCNT dans libnds et POWCNT1 sur gbatek) permet d'activer ou de désactiver certaines puces de la DS pour réduire la consommation. Côté ARM7 (connu alors sous POWCNT2), il contrôle le son et le Wifi. Côté ARM9, il contrôle les processeurs graphiques, permettant d'activer ou de désactiver séparément la 2D, la 3D, etc. Tout ce qu'il y a à faire, c'est :

if (lid_closed()) {
u16 power = REG_POWER;
REG_POWER = 0;
while (lid_closed()) swiWaitForVBlank();
REG_POWER = power;
}
la position du capot étant donnée par le 7eme bit des "boutons" de la console. Le coeur du fonctionnement étant évidemment la boucle "while(lid_closed) waitForVBlank() qui va utiliser les fonctions du BIOS de la DS pour mettre le CPU en pause jusqu'à ce qu'une interruption se produise (en l'occurrence un retour d'écran), et ce en continu tant que le capot est fermé. Au lieu d'exécuter 66 millions d'instructions par secondes, le processeur se contentera alors d'environ 600 à 1200 d'entre-elles (à la grosse louche, hein) et le rendu graphique est désactivé.

Evidemment, pour faire "pro", il faudrait aussi signaler au co-processeur (l'ARM7) de mettre en berne le son (sauf si on programme un iPoDS) et le Wifi (sauf si un transfer de fichier est en cours). En clair, si l'ARM7 pourrait gérer sa puissance de manière autonome, il reste préférable de le reléguer dans un rôle d'esclave.

Ma première tentative pour appliquer ça n'a pas été franchement probante, mais quelques "printf" m'ont vite révélé mon erreur : je n'ai encore aucune routine d'interruption pour le 'retour d'écran' (VBLANK) et les interruptions VBLANK sont carrément masquées par mes programmes. Résultat, swiWaitForVBlank() attend indéfiniment :P Si j'y remédie et que je passe à du "waitForVBlank" dans ma boucle principale également, c'est toute l'application qui devrait devenir nettement moins gourmande.
while(REG_VCOUNT>192); // wait for vblank
while(REG_VCOUNT<192);
c'est indigne d'un vétéran. Quand mes étudiants codent comme ça, je les menace de leur imposer de coder sous DOS.

Et si je vous raconte tout ça au conditionnel, c'est que mon routeur WiFi à la maison m'a lâchement laché, rendant le développement DS aussi pratique qu'à Bâle, le temps libre en moins.

edit: après essai, curieusement, le son est mis en veille lui aussi, automatiquement et sans communication explicite de ma part entre ARM7 et ARM9 ... Ne loupez pas non plus le commentaire très intéressant de thoduv (lapinou jumps) pour passer de la théorie à la pratique "pro".

Sunday, July 26, 2009

avant Bilou ...

Avant même Calimero, se basant sur Rick Dangerous, mon frère me sort un niveau pour un jeu de plate-forme mono-écran qu'il baptise "Logic Labyrinth", rempli d'interrupteurs et de pièges en tout genres. Le concept me plait et je relancerai l'idée plusieurs fois (chaque fois que je découvre un nouvel environnement de programmation, en fait). Logic labyrinth manquait d'un personnage, par contre. Il devait s'agir d'un "char de l'espace", ce qui ne passait pas trop mal du temps de LOCO 64, mais plus difficilement après avoir découvert Giana Sisters. Je vous laisse donc découvrir cette petite illustration millimétrée de deux protagonistes destinés à s'attaquer au fameux labyrinthe, qui doit précéder la rencontre avec Piek de deux ans au moins.
Une balle aux cheveux hirsutes et une asperge à casquette ... Eh oui. On reconnait déjà le tandem "Bilou et Bouli" même si le style n'a encore rien à voir. A noter que Bouli étant arrivé sur le tard, son 'look' a souvent changé au fil du temps. Il était de bon ton, à l'époque, de prévoir un deuxième perso pour le joueur qui prendrait la manette 2 (ah, époque bénie ou une manette de console ne coûtait rien ;)

The image above is the Level 1 for a never-realised game of mine : Logic Labyrinth. With a strong influence from Rick Dangerous, my brother imaged one vicious puzzle screen where a hover-tank would avoid traps and cleverly activate switches to reach its goal. Since I wasn't too happy with the "hover tank" idea as a character, i started investigating a funnier team: a blue ball and a tall guy with a cap. This all took place years before we met Piek and it could be viewed as the very first step towards Bilou and Bouli the way we know them today.
Over the years (I was roughly 10 at the initial attempt on Logic Labyrinth), I reviewed the concept several times, being somehow a fan of puzzle platformers. Drawing inspiration from Misadventure of Flink or Pushover, the game has been renamed "Mo, the sorcerer apprentice" or "Nono in the Maya Zone", but it never grew bigger than a dozen of lines of code.
première tentative, Bouli en "négatif couleur" de Bilou, mais tout aussi rond que lui, qui apparaît parmi les ennemis d'une "technical zone" très largement inspirée de la "Chemical Zone" de Sonic 2 (découvert début '93).
C'est peut-être un peu trop "cheap". C'était bon du temps de Mario Bros. ou de Chip & Dales sur la NES, mais plus à l'époque de Sonic & Tails où même Mario et Luigi commencent à ressembler à Laurel & Hardie.

Second essai à peine plus ancien: Bouli en tant que "Superlapin", sans doute inspiré de Mr. Nutz. Mon frère n'aime pas. On oublie. A noter qu'à l'époque, Bilou porte des gants et a encore des bras.

C'est à Sparenduin, notre "pépinière de jeux vidéos" que naîtront les habitants de la "Pipe Zone". Il ne manque plus qu'un sourire au Pipe Meccano pour se transformer en Bouli tel que nous le connaissons.

Et pour revenir au jeu Logic Labyrinth, il aura été "revu" à plusieurs passages successifs à Sparenduin, une fois en "Nono in the Maya Zone" (en avril '96, influence probable de Push Over) puis en "Mo, l'apprenti sorcier" (influencé par Misadventure of Flink"), mais je n'en ai encore jamais commencé une tentative de programmation "sérieuse".

Still on the 'historical' side, can show you the very first spritesheet of Bilou (still named 'Boudy the Bubble' when drawn, though the name 'Bilou' appeared that very day) that Piek brought us on September the 25th, while i was working on a "maze race" game. Just above, you can see a collection of "alternative designs" for Bouli, first as "color opposite" of Bilou (plus hat), then as "über bunny". None of them were kept (hopefully ^_^) and i'd be tempted to say that de "pipemans" designed to be baddies in the 'Pipe Zone' might be announciating the current design.

Quant au nom "Bilou", c'est au moment de sauver les premiers essais de course dans les labyrinthes (précurseurs de "Bilou RPG") sur diskette qu'il apparaît. Piek m'avait affublé de ce sobriquet tout au long de l'après-midi, il deviendra officiellement le nom du personnage quelques heures plus tard.

Dernière pièce de musée, donc, cette "planche de sprites" dessinée et apportée ce jour-là par Piek, où Bilou s'appelle encore "Boudy" ou "Bubule".

PS: Oui, désolé, je suis dans un trip nostalgico-historique cette semaine-ci. Je promets le retour du développement sur DS prochainement ...

edit Découvrez M.G.T, la source d'inspiration de Logic Labyrinth, dans Pix'n'Love #13.

Thursday, July 23, 2009

Calimero

Difficile de vous parler de mon expérience de la programmation de jeu sans vous parler de Calimero. Plus qu'un jeu, c'est pratiquement toute une page d'histoire en ce qui me concerne. Celà se passe au début de mes années de secondaires, donc entre 1991 et 1994.

La construction du jeu est clairement inspirée par le jeu Sonic the Hedgehog sur MasterSystem qui cartonnait à l'époque sur les écrans de la maxithèque: bumpers, pics, et bonus / powerup dans des "télévisions". La comparaison s'arrête là : j'avais dans les 13-14 ans, et bien loin du niveau de la Sonic Team ...

"Calimero against the Black Empire" is more than a game: it's almost the complete story of my early game-programming experiments, between 1991 and 1994. I was roughly 14, in a world ruled by floppy disks, my brother and I were impressed by the first episode of "Sonic the Hedgehog" on MasterSystem and so appeared our first levels featuring bonus-in-televisions. While the initial project was to realise this on C64 (see sprites below), it was my first big BASIC project on a PC ... an 8086 XT to be precise with 720x348 Hercules graphic display.

Le projet a commencé alors que je recevais à peine mon premier 8086 XT, et je m'orientais plutôt vers une réalisation sur le C64, comme en témoignent ces premiers essais de sprites millimétrés. De là aussi le look très "géométrique" des décors. Pourtant, avec l'avancée de ma lecture du langage EPbasic, c'est bel et bien sur PC que l'aventure aura lieu. Je passe donc mes grandes vacances à compter les petits carrés et à encoder tout ça en "passe 21 pixels, trace 20 pixels en blanc, à la ligne, passe 20 pixels ...".

Si je ne peux pas vous donner une historique plus exacte, c'est qu'avec un disque dur de tout juste 20 MB, toute l'évolution du projet s'est déroulé sur diskettes 5'1/4 un peu dures à relire aujourd'hui ... Et avec un PC qui ne retient pas la date, ... Quelques versions diskettes seront refilées à mes copains de classe programmeurs Julien Collaer et Cédric Dupont.

My brother drew the level for 4 worlds -- namely fire, water, pyramids and pipes -- that Calimero the black chick will travel to save his sweetheart Priscilla from the clutches of the Evil Black Empire. Okay, admittely, nothing impressive in that scenario by today's standards, but keep in mind that this was the scenario of virtually *any* platformer by then. Calimero's favourite sentence "That's too much unfair" is really the corner stone of my brother's level design: you'll have to jump into that fake lava river to find the level exit. Don't rush to the obvious exit, which is fake and will just make spikes appear all over the place that will kill you. Even with the cutest graphics, with such levels, it would be hopeless to work on Calimero on DS...

La première version qui voit le jour pour PC avec carte monochrome Hercules à la résolution improbable de 720x348 dans le "niveau du feu". Mon frangin (Cyborg Jeff, uniquement connu en tant que "Piet" à ce moment-là) qui était déjà mon scénariste pour la bande dessinée, me fournit un scénario en béton (la belle priscilla enlevée par l'Empire Noir) et des niveaux dans 4 mondes originaux (le feu, l'eau, les pyramides et les tuyaux)... On s'en plaint maintenant dans Super Princess Peach, mais à l'époque, c'était plutôt bien vu.

Non, le vrai problème avec ces niveaux, c'est l'influence de Rick Dangerous. Des "picots invisibles", un faux drapeau (fausse sortie du niveau), et quasi systématiquement la fin se trouve derrière une fausse mare de lave, etc. C'est une des raisons pour lesquelles il n'y aura jamais de portage de Calimero sur DS, même si je faisais quelque-chose d'aussi réussi graphiquement que le mockup de 'New Zealand Story' par Kenneth Fejer.

I don't precisely realise those flaws by that time, and I will spend much of my leisure time to precisely draw every screen on a large sheet of paper, with a 1mm=2px scale, before the level is translated into LINE(xo,yo)-(xd,yd) and PAINT(xc,yc) statements. The coordinates of every bonus and hazard hitbox are scribbled with a coloured microball pencil ... I had only access to the computer three days a week, and only for one hour (parental rules :P), so such preparation were a must. Programming sessions, however, often consist of repeatedly asking the screen to be repainted as being one pixel off could make a PAINt command to overflow and fill the whole screen >_<. A missed "screen exit detection" -- a request to paint a sprite out of the screen -- will interrupt the execution with an infamous error message from the BASIC : more "IF XX < ... THEN GOTO ..." is needed :P

Et pourtant, je persiste. A grand coup de feuilles de listing sur lesquelles je prépare minutieusement les commandes "line" et "paint" du BASIC à l'échelle qui définiront chaque écran, des tests pour chaque bonus et pour chaque zone mortelle. Si ça permet une certaine liberté, c'est long. Terriblement long à mettre au point (un seul pixel de loupé et la commande "paint" recouvre tout l'écran >_<). Je suis toujours dessus en septembre '93 quand mon frère rencontre Pierrick et commence à envisager une version en couleur sur ... Amstrad CPC. Le projet ne commencera jamais, mais jettera les base de Bilou. A Pâques 1994, je migre vers un 386 avec VGA et carte son. Et là, horreur : le mode d'écran "SCREEN 3" que j'utilisais jusque là n'est plus valable. Il faut tout repasser en 640x480, mais je gagne quelques couleurs au change. Je vais même aller jusqu'à programmer enfin le premier boss avec l'aide de Pierrick, reportant méticuleusement le dragon dessiné en Deluxe Paint via des pages entières de feuilles quadrillées (genre 'point-de-croix' pour ceux qui connaissent) des zones importantes, que je réencode en BASIC. Sans services du genre "wotsit", l'utilisation des .pcx est à cette époque réservée à ceux qui ont pu s'offrir "graphic gems" ou un bouquin du genre.

When I purchase a VGA graphic card and a Master Boomer sound card for my 386 in easter '94, I realise in terror that the 720x384 mode is Hercule-specific and no longer supported. The whole game has to be updated -- but by the same time, colours can be added. With some help from Pierrick, Calimero will at least fight against his first boss -- a dragon drawn with Deluxe Paint and hand-transcoded with several 20x20 tiles on A4 draft, squared sheets: there was no WOTSIT service by that time to help me understand how to process PCX or LBM file format, and definitely no function library to do the job for me. In its ultimate shape, Calimero will have a 10sec music sample looping during the boss fight and a "cinematic" conclusion where lava is replaced by water, flowers grow and blue bunnies frolic all over the scene on a speaker-rendered "merry melodies" theme.

J'irai même jusqu'à programmer une petite "cinématique" de fin de monde, réutilisant les lapins servant de NPC dans "Bilou RPG" (que je mêne en parallèle) et la goutte d'eau qui sert de pièce d'or dans Keen IV et faire un happy end sur la musique du final "Merry Melodies" des cartoon de mon enfance.


Alors que Juin '94 arrive, le projet s'essoufle. C'est définitivement trop exigeant pour un gameplay qui lasse. Pour pouvoir jouer la musique de Pierrick pendant le boss (en fait, une interprétation du thème de Terminator sur le synthé de mon frère), j'ai "acquis" le QuickBasic 4.5, étudié attentivement l'aide qui m'ouvre de nouvelles perspectives : le stockage de sprites "en natif", la manipulation de fichiers, et surtout la programmation structurée, enfin libérée de la numérotation des lignes. De nouveau, c'est surtout "Bilou RPG" qui en bénéficiera, Calimero ne servant que d'explorateur hasardeux pour ces techniques.

As I get more comfortable with 256 color screen mode and find ways to go beyond a simple "XOR" display, the project is left aside as I turn towards the Bilou RPG project using recently developped sprite editors. Calimero will remain forgotten until June '95 where my bored brother will use Recreational Software Design Game-Maker to revive the first twp levels. The hope to see the water, pyramid and pipes zone didn't last very long, however, as G-M hardly support most of the gameplay features (secret passages, bumpers, and switch between gravity-affected player and helicopter power-up in the same level).

Ce n'est qu'en juin '95 que mon frère, armé cette fois du GameMaker de Recreational Software Design et des graphismes (très inspiré de Sonic, il faut le dire) de mon "Panzer III", nous gratifiera d'un "calimero 2". Je suis sûr qu'il avait prévu de faire (enfin) une réalisation des niveaux de l'eau, pyramide et du monde des tuyaux, mais même le premier boss passera sous silence. Les passages secrets, les bumpers et l'hélicoptère, ce n'était vraiment pas pour le GameMaker, rien à faire.


Maintenant, éteignez votre ordinateur et allez vous coucher

Monday, July 20, 2009

Carmen sans Diego

Entre deux couches-culottes, je m'imaginais cette nuit un portage du célébrissime "Carmen Sandiego" sur ma petite DS. Ca doit être le premier jeu (Broderbund Software, 1985) que j'ai pu faire tourner sur mon tout premier PC (un 8086 pré-AT avec un écran monochrome aux résolutions improbables et un lecteur de diskettes 5'1/4), à savoir que son côté ludo-éducatif avait convaincu les autorités parentales ;)

Mis à part la collecte de graphismes pour illustrer tous les haut-lieus de la culture internationalle (Gizeh, la grande muraille, etc.) Le principe du jeu était simple et efficace. on atterit à Londres, 2 P.M. Il va falloir visiter bibliothèques, musées et autres pour trouver un indice qui nous permettra de découvrir dans quelle direction s'est enfui le voleur de la joconde. Hmm. Il s'est renseigné sur les pharaons (bon, parfois, c'était un peu plus corsé quand-même, mais ça reste du ludo-éducatif pour les 8 ans et plus) ... je note. Mais il faudra aussi suffisamment d'information sur son apparence pour pouvoir obtenir un mandat d'arrêt à son nom.

Bien sûr, à l'heure Layton/Wikipedia, il faudrait un peu revoir la mécanique de jeu pour qu'il reste plus intéressant pour nos têtes blondes de se creuser les méninges que de faire appelle à Internet. Petit rafinnement, je me disais "pourquoi ne pas piocher dans notre richesse locale et se faire un 'A la poursuite de Rastapopoulos' avec notre détective national.

Et je ne suis pas le seul à avoir eu l'idée et l'éditeur MindScape nous a gratifié du 'Mystère au bout du monde', qui est décevant au possible, selon la critique. Quand on voit que MindScape nous a aussi gratifié d'un "Fort Boyard DS" et d'un "Intervilles sur Wii", on n'est même plus surpris.

Que se passe-t'il donc dans le monde du jeu vidéo? Comment encore blâmer la piraterie quand les chefs-d'oeuvre d'antan (et les plus récent, cf. mon avis sur Action Loop) sont bafoués et réduits au niveau de collection de minijeux fadasse entre les cases d'une bande dessinée.

Allez, je vous parie qu'on verra bientôt "Lea Caissière" qui doit cliquer sur les articles qui tournent façon "astro-fire" quand le code-barre devient visible ... ou réassortir les rayons sur un fond de Tetris.

PS: Pour ceux qui voudraient tenter une adaptation homebrew (au hasard, Stravingo ?, à partir de ton Treasures of Gaia, ça doit être jouable ;) je vous propose donc de tester l'original sous DosBox ou de jeter un oeil à la vidéo du gameplay version MSX.

Monday, July 13, 2009

Les plate-formes


Le prochain "gros challenge" pour mon moteur de jeu (sur lequel je cogite actuellement, en tout cas), c'est sans hésitation les plate-formes. Tous ces objets mobiles, assenceurs, radeaux, etc. qui tout en ayant leur comportement propre altèrent celui du personnage ou agissent comme des parois solides. Bref tout une série d'objets qui vont venir perturber les belles règles de gestion des collisions du moteur de jeu.
Technically speaking, the next challenge for my game engine is platforms. Those moving objects you'll find in any decent platformer that have their own pattern and that alter the player's behaviour (and sometimes ennemies' as well) to create interesting levels and gaming experience. It's still very sketchy in my mind, in "look for use cases" stage that happens to take place by drawing gaming moments in this project -- fairly funnier than rationale UML, if you ask ;)

J'en suis encore fort au stade "conceptuel", qui est franchement sympa dans ma manière de travailler, puisqu'il s'agit de "mises en situations" à coup de crayon pour voir si la solution que j'ébauche tient suffisamment compte des différents aspects. Du style "non, on ne peut pas lier définitivement un contrôleur à une plate-forme, parce qu'il pourrait y avoir aussi des petits vers sur les champignon-ascenseurs".

Après deux ou trois tentatives peu convaincantes, j'en arrive à la conclusion que mon système "un contrôleur par état" est un peu limitatif. De la même manière que j'essaie de faire de la composition de micro-programme dans mes recherches sur les protocoles réseaux, pourquoi ne pas faire de la composition de contrôleurs dans le moteur de jeu ?

Encore trop tôt pour commencer à faire des changements dans le code, mais on dirait bien que ce genre de mécanisme qui transforme la fonction de contrôle unique en "lire_le_pad -> pousser_un_objet -> suivre_une_pente -> marcher" s'appliquerait aussi bien aux objets déplaçables ou aux pentes fixes (en plus des plate-formes mobiles). Le même micro-comportement "marcher" pourrait prendre comme "input" la lecture du pad directionnel ou la position relative de Bilou par rapport à un appleman ...

Plein de choses intéressantes, donc, que je continuerai à creuser dès que j'aurai un peu dompté la forêt vierge qui me sert de jardin.

The thinking about supporting moving platforms also questions the way i'm coding controllers, that is, a large chunk of code that does everything a specific state needs, including reading Dpad, adjusting speeds, checking that the current move is possible and make it possible if speeds need to be aligned to avoid entering walls. Such an approach doesn't let me easily alter behaviour due to a lift or a pushable ennemy.

Instead, i'll investigate the option of a chain of controllers, each of them doing only a simple action such as reading the pad, or updating speeds according to momentum. It could also be "zero speed if character pushes into the moving block's direction" or "prevent the character from falling as long as he's on a platform". Still a bit early to change all the code base, but ...