BIG EGG · Postes et employés · Décisions prises
Des fourneaux, une épicerie, un comptoir takeout et des gens pour les tenir. Ce que chaque poste apporte réellement, comment un employé se décrit en données, et comment les files de salle et de rue restent indépendantes.
La correction la plus importante
Ma première version posait comme règle qu'un employé reste toujours plus lent que le joueur. C'est faux, et ça tuait le genre. La courbe visée est celle des jeux d'accumulation : au début, faire le travail soi-même est nettement plus rapide ; à terme, la brigade est plus rapide de plusieurs ordres de grandeur.
Concrètement, à maturité : tu veux livrer une assiette, le serveur t'a déjà doublé. Tu ouvres le menu de recettes, le cuisinier a déjà posé deux plats sur l'étagère. Tu peux toujours mettre la main à la pâte, et ça ne gêne jamais — mais ça cesse d'être ce qui fait tourner la boutique.
Trois choses. Les compétences doivent être multiplicatives et sans plafond dur, pas des bonus plats. Le débit doit être lisible : quand la brigade double, le joueur doit le voir sur l'ardoise, pas le déduire de ses recettes. Et surtout, tout ce que la brigade touche doit exister en données partagées — d'où l'ardoise.
Le joueur qui contribue reste un choix valable dans les premières heures. Ensuite sa vraie contribution est ailleurs : il plonge, il rapporte des ingrédients, il achète des postes et des gens.
Le point structurant
Aujourd'hui une commande n'existe nulle part. Elle est un champ sur le client, lisible seulement à proximité, et qui s'efface de sa mémoire après order_memory_seconds. C'est de la mémorisation, pas une file de travail. Un cuisinier automatique n'a rien à lire, un serveur n'a nulle part où écrire.
L'ardoise est la file de travail du restaurant, et la seule source de vérité sur ce qui reste à faire. Elle se construit en premier, et elle a de la valeur toute seule : même sans un employé, elle supprime la mémorisation.
{
"table": 3, // un tabouret par table: l'indice désigne le client
"recipe": "pepper_scramble",
"state": "pending", // pending → cooking → ready
"station": "", // poste qui l'a prise, vide tant que personne
"superior": false, // passé par l'épicerie
"written_at": 812.4
}
Repérer une commande l'inscrit. Une fois l'ardoise débarrée, le geste de lecture actuel — s'approcher assez d'un client qui attend — écrit directement la ligne. Plus de mémorisation, plus d'effacement au bout de huit secondes : ce qui a été vu une fois est acquis.
Le serveur fait exactement la même chose, à sa propre distance de repérage. C'est le même code, appelé par deux acteurs différents.
Trois règles qui évitent les conflits :
cooking : deux cuisiniers ne se disputent jamais la même commande, et le joueur non plus.Statistique associée : order_board_slots (base 6). Une ardoise pleine empêche d'inscrire une commande de plus — c'est le levier qui empêche la brigade de tourner à vide.
Le gros texte qui annonçait le plat dès qu'un client s'asseyait est supprimé. Il divulguait la commande avant même qu'on l'ait prise, ce qui vidait de son sens tout ce qui précède. Le message dit maintenant seulement qui attend.
Les lieux
Le restaurant n'a qu'une cuisson à la fois : cooking_recipe et cooking_remaining sont des champs uniques sur la scène. Un deuxième four est impossible tant que c'est le cas. La généralisation suit le précédent des tables : une liste de postes, un compte par statistique, aucune position écrite à la main.
| Genre de poste | Statistique | Base | Ce qu'il apporte |
|---|---|---|---|
stovefourneau | stove_count | 1 | Débit pur. Deux fours, deux cuissons en parallèle. |
takeoutcomptoir de rue | takeout_counter | 0 | Une recette maître produite en série. File et service propres, sans table ni vaisselle. |
spicesépicerie | spice_station_count | 0 | Une étape de plus, un plat supérieur garanti. |
C'est le meilleur des trois postes, parce qu'il ne fait pas la même chose que les autres. Il ne cuisine pas : il reprend un plat déjà cuit et lui ajoute une étape, au terme de laquelle le plat devient supérieur — pas au hasard, à coup sûr.
fourneau → assiette normale → épicerie → assiette supérieure → service
prix de vente = prix de base × superior_payout // base 1.5
Une seule statistique, superior_payout, dit ce que vaut le raffinage. Une branche d'upgrades la monte : 1.5, puis 1.8, puis 2.2. C'est une progression qui ne demande aucun contenu neuf, seulement du réglage — le genre de levier qui vieillit bien.
Le coût est du temps et un poste occupé. À toi de décider si ça vaut le coup, et cette décision change avec le nombre de cuisiniers : à un cuisinier, raffiner c'est perdre du débit ; à quatre, c'est de la marge gratuite.
La compétence plating reste, mais devient le chemin sans épicerie : une chance qu'un cuisinier doué sorte un plat supérieur directement du fourneau. L'épicerie est la voie garantie mais lente, plating la voie gratuite mais aléatoire. Les deux nourrissent le même drapeau sur l'assiette et la même statistique de prix — un seul concept, deux façons de l'atteindre.
Le comptoir est adossé au mur nord, plus près du trottoir que l'ancien comptoir à boissons. Il ne vend plus un article abstrait : le joueur choisit une recette maître parmi les vrais plats dans l'onglet Takeout de la console, puis la cuisine en série en tenant directement l'action au poste. Chaque exemplaire consomme les ingrédients de la recette et rejoint une réserve bornée.
takeout_recipe, takeout_stock, la cuisson en cours et la règle de réapprovisionnement sont persistants. Tant que la réserve, une file ou une cuisson porte l'ancienne recette, le poste refuse d'en mélanger une autre. Le joueur peut enchaîner jusqu'à takeout_stock_capacity; un cuisinier attend que le stock passe strictement sous X, puis poursuit son lot jusqu'à Y.
evaluate_takeout_join() est indépendant de evaluate_queue_join(). Le premier est appelé lorsque le passant croise physiquement le comptoir, le second à la porte principale. Un passant intéressé rejoint la seconde file sur le trottoir devant le comptoir; il ne franchit jamais la porte, ne réserve aucune table et ne crée aucune vaisselle. Aucun tracé décoratif ne simule la file : les clients et leurs positions en sont l'état visible.
| Levier | Rôle |
|---|---|
takeout_queue_capacity | Nombre maximal de passants dans la file propre au comptoir. |
takeout_appeal | Part des passants susceptibles de vouloir la recette sélectionnée. |
takeout_service_speed | Ventes automatiques par seconde quand un plat fini est disponible. |
takeout_stock_capacity | Plats finis accumulés avant que le poste s'arrête. |
takeout_cook_speed | Coefficient propre à la cuisson de ce poste. |
takeout_priority | Poids de cette tâche face aux commandes de salle pour les cuisiniers. |
Le joueur peut tenir le poste exactement comme un four, sans ouvrir de sélecteur. Un cuisinier oisif compare la priorité takeout à celle de l'ardoise, mais ne réserve le comptoir que lorsque le stock est sous X; il termine alors jusqu'à Y. Son rendement combine craft, station_affinity.takeout, son affinité de recette et la vitesse propre au comptoir.
Le service au client reste automatique : le délai dépend de takeout_service_speed et vaut environ 30 secondes par client sans upgrade ni aide. Le chronomètre ne descend qu'une fois la tête de file arrivée devant le comptoir. Lorsque la réserve est pleine, le joueur qui continue à tenir l'action ne tente plus de cuisiner : il accélère le service de 30 %. Un serveur libre peut réserver une seule place au comptoir selon la même comparaison de priorités que ses tâches de salle et ajoute 30 %. Les deux aides sont additives, donc 1,6× ensemble. Ce partage garde un geste de cuisine intéressant sans transformer chaque vente de rue en corvée. Le manque de stock ne retire pas de réputation; le passant continue sa route.
Le stock déjà cuisiné peut se vendre hors scène selon sidewalk_traffic, l'attrait et la vitesse de service. Aucun plat n'est produit magiquement pendant l'absence. Le compte rendu indique les plats vendus, les pièces encaissées et la rupture éventuelle.
takeout appartient au vocabulaire des postes dans Godot, PHP et l'éditeur.Les trois champs de cuisson deviennent une entrée dans un tableau de postes. player_is_tending_stove() devient tended_station() : rester appuyé sur l'action près d'un poste accélère ce poste. Une recette gagne un champ station (défaut stove) ; une recette dont le poste manque disparaît du menu et des commandes toute seule, sans code dédié.
Nouveau
Choisir le menu du jour depuis le fourneau n'a déjà plus tellement de sens ; avec une brigade, ça n'en aura plus du tout — le joueur ne sera plus celui qui cuisine. Un meuble à part, dans un coin de la salle :
menu_slots. C'est l'écran qui existe déjà, déplacé.served_rate()), elle n'est visible nulle part — et c'est précisément le chiffre qui doit rendre lisible chaque achat de brigade.La console est construite avec quatre onglets : magasin, menu, brigade et takeout.
Nouveau
Avec plusieurs cuisiniers qui posent des plats et plusieurs serveurs qui les prennent, l'étagère devient le point de rencontre de tout le restaurant. Elle ne peut pas rester un compteur.
shelf_slots, dessinés comme les tables — une grille dont on ne montre que les cases ouvertes.Les gens
Nouvelle collection employees, du même rang que enemies ou recipes, avec sa racine d'adressage, ses compteurs vivants et ses crochets.
employees.chef_marguerite.total_dishes_cooked // compteur vivant
employees.pablo.hired // valeur calculée
employees.pablo.on_hired // crochet
| Champ | Nature | Rôle |
|---|---|---|
role | server · cook | Décide du type de slot et de la boucle exécutée. |
hire_cost | entier | Prix d'embauche. Seul coût. |
skills | carte id → niveau | Le cœur du personnage. Vocabulaire fixe, valeurs libres. |
station_affinity | carte genre → coefficient | Fourneau, épicerie ou takeout. 1.0 = neutre. |
recipe_affinity | carte recette → coefficient | La spécialité maison d'un cuisinier. |
modifiers | liste | Bonus passifs, sous la source employee:<id>. |
conditions | liste | Conditions d'apparition, comme une case scellée. |
scope | dimension · meta | Défaut dimension. |
Les modifiers travaillent gratuitement. Un employé embauché pose ses modificateurs sous une source nommée, comme un équipement ; le renvoyer appelle remove_modifiers_by_source(). Tout ce qui se traduit en statistique existante ne demande aucun code neuf.
server_count base 0 // 1, puis 2, puis 3 par upgrades
cook_count base 0
Les nœuds first_server, second_server… ajoutent +1. Aucun code ne connaît leurs noms — la leçon des tables, où second_table et third_table étaient codés en dur et ont dû être défaits.
Un employé de portée dimension est perdu au changement de dimension et se rachète au prix fort, alors que le slot, lui, est acquis. C'est la seule dépense récurrente du système, et elle est volontaire : rien ne t'oblige à reprendre le même. Un employé meta reste, et son prix d'embauche doit refléter ça.
Le vocabulaire
Vocabulaire fixe déclaré dans un constant, comme ROOM_BEHAVIOURS. Toutes multiplicatives : c'est ce qui permet à la brigade de finir des ordres de grandeur devant le joueur.
| Compétence | Effet |
|---|---|
paceallure | Vitesse de déplacement. La plus visible, et celle qui décide vraiment du débit d'un serveur. |
staminaendurance | Actions avant une pause courte. Un employé fatigué ralentit, il ne s'arrête jamais. |
| Compétence | Effet |
|---|---|
sightcoup d'œil | Distance à laquelle il repère une commande et l'inscrit sur l'ardoise. Un coup d'œil court oblige à faire le tour des tables ; un coup d'œil large couvre la salle depuis un seul point. Séparée de l'attention parce qu'elle se règle en pixels et se voit à l'écran. |
attentivenessattention | Délai avant de réagir à ce qu'il a repéré, et vitesse d'écriture. Une attention basse laisse traîner alors qu'il voit très bien. |
charismacharisme | Multiplie le pourboire des repas qu'il a servis lui-même. |
trayplateau | Assiettes portées par voyage. Passer de 1 à 2 change plus le débit que n'importe quel bonus de vitesse. |
tidinessdébarrassage | Vitesse de ramassage et de lavage. Forte tidiness et faible charisma font un commis de salle — la spécialisation naît des valeurs, sans champ « métier ». |
poisesang-froid | Les clients de sa salle perdraient leur patience plus lentement tant qu'il est visible. Cette compétence reste publiée mais n'est pas encore lue. |
| Compétence | Effet |
|---|---|
craftmétier | Vitesse de cuisson propre, multipliée ensuite par les affinités. |
platingdressage | Chance qu'un plat sorte supérieur sans passer par l'épicerie. |
thriftéconomie | Chance de ne pas consommer un ingrédient. Convertit du temps de donjon en marge. |
misemise en place | Temps mort entre deux commandes prises sur l'ardoise. Compte double quand les plats sont courts. |
nosenez | Choisit la commande la plus rentable plutôt que la plus ancienne. Une compétence de décision, pas de vitesse. |
« Spécialiste takeout », « rôtisseur », « commis de salle » ne sont écrits nulle part : ce sont des profils de valeurs. Un cuisinier avec station_affinity.takeout = 1.6 et 0.7 ailleurs privilégie naturellement le comptoir. Pas de liste de métiers à maintenir en parallèle des compétences.
Les boucles
OISIF → la tâche la plus prioritaire dans son rayon
1. un client assis sans commande inscrite → repérer, écrire sur l'ardoise
2. une assiette ready sur l'étagère → porter jusqu'à la table
3. une assiette sale sur une table → ramasser, laver
4. file takeout + stock prêt → tenir le comptoir, service +30 %
rien → retour au poste d'attente
L'ordre est pondéré par ses compétences : tidiness élevée remonte le débarrassage, attentiveness la prise de commande. Deux serveurs opposés se répartissent le travail sans qu'aucun code ne les coordonne.
OISIF → un poste libre de son genre + une ligne pending qu'il peut faire ?
oui → réserve la ligne (cooking), occupe le poste, cuit
à la fin: pose sur l'étagère, passe la ligne en ready
non → attend au poste
« Qu'il peut faire » veut dire : ingrédients présents, vaisselle disponible, poste requis libre. Le choix entre plusieurs lignes possibles est le seul endroit où nose intervient. Un cuisinier affecté à l'épicerie reprend les assiettes normales de l'étagère au lieu de lire l'ardoise.
Le vrai enjeu
GameState garde encore l'échafaudage du futur restaurant entièrement autonome :
restaurant_operations = {
"automated_cooking": false,
"automated_service": false,
"automated_cleanup": false,
"automated_supply": false,
"pending_simulation_seconds": 0.0,
}
Ces quatre drapeaux ne sont pas encore allumés par la brigade. Le takeout possède toutefois une voie plus stricte et déjà active : des secondes s'accumulent hors scène seulement lorsqu'un stock fini peut réellement se vendre.
automated_cooking : futur calcul des recettes et ingrédients hors scène;automated_service : futur débit de la salle;automated_cleanup : future gestion de la vaisselle;automated_supply : futur réapprovisionnement.Au retour de plongée, le takeout convertit ces secondes en ventes selon le trafic, l'attrait et la vitesse de service, puis borne le résultat par takeout_stock. Les cuisiniers ne fabriquent rien en l'absence du joueur : le compte rendu montre uniquement ce qui était prêt et a trouvé preneur.
Tranché
| Question | Décision | Conséquence |
|---|---|---|
| Portée d'un employé | Déclarée par la fiche, défaut dimension | Réutilise scope. Quelques employés rares en meta. |
| Catalogue | Fixe, embauche conditionnée | Réutilise les conditions. Aucune interface de recrutement à écrire. |
| Coût continu | Aucun — prix d'embauche seulement | Le rachat à chaque dimension est la seule récurrence. wage retiré de la fiche. |
| Geste du joueur | Conservé, et il inscrit sur l'ardoise | Le repérage remplace la mémorisation. Même code pour le joueur et le serveur. |
| Épicerie | Raffinage garanti, coefficient par upgrades | Une statistique, superior_payout. Une branche entière sans contenu neuf. |
| Takeout | Recette maître et réserve cuisinée | Le joueur ou un cuisinier produit; la file de rue est servie automatiquement, sans table ni vaisselle. Au stock plein, le joueur peut accélérer le service de 30 %; un serveur priorise librement une seconde aide de 30 %. |
| Vente hors scène | Stock fini seulement | Le trafic, l'attrait et le débit bornent les ventes; aucune production magique. |
charisma perd son contrepoids en supprimant le salaire : sans part prélevée, le pourboire est du gain pur. Il faudra que le charisme coûte à l'embauche plutôt qu'au service — un serveur charismatique doit être nettement plus cher qu'un serveur rapide.
La route
Chaque phase est jouable et testable seule. Aucune ne laisse le jeu à moitié.
Le tableau, ses lignes, sa persistance, son affichage. Repérer un client inscrit sa commande. Fin de la mémorisation. Aucun employé, et déjà un gain net.
La cuisson unique devient une liste de postes pilotée par stove_count. Deuxième four. La console de gestion prend le menu et l'ouverture. Le gros de la refonte est ici, sans concept neuf.
Emplacements visibles, plat identifiable, ramassage sans ambiguïté. Petite phase, mais tout ce qui suit passe par là.
Genre de poste spices, drapeau supérieur sur l'assiette, superior_payout et sa branche d'upgrades. Aucune recette neuve : ce sont les mêmes plats, mieux vendus.
Poste takeout contre le mur nord, recette maître réglée à la console, réserve bornée et seconde file devant le comptoir. Le joueur le tient directement; les cuisiniers se déclenchent sous X et remplissent jusqu'à Y selon takeout_priority. Une fois plein, le geste du joueur devient une aide de service de 30 % et un serveur disponible peut en ajouter une autre selon ses priorités. Le service automatique ne dépend ni des tables ni de la vaisselle.
Collection employees, page de gestion, vocabulaire de compétences, embauche, slots par statistique. Les modifiers s'appliquent dès cette phase : un employé embauché est déjà un bonus avant même de bouger.
L'agent qui marche : repérage, écriture, service, débarrassage, priorités pondérées. La phase la plus longue et la plus visible.
L'agent aux postes : lecture de l'ardoise, réservation, cuisson, dressage. Les affinités entrent en jeu. C'est ici que la courbe exponentielle commence à se voir.
Les quatre drapeaux s'allument selon la brigade, pending_simulation_seconds se dépense au retour de plongée, la réserve devient la seule limite. La phase qui donne rétroactivement un sens à toutes les autres.
Neuf phases donc, le takeout s'insérant après l'épicerie : il réutilise les recettes et le travail continu, mais garde son stock et sa clientèle séparés.
Le coût
Trois montées de version, pas une : 16 pour l'ardoise, les postes et l'étagère, 17 pour l'épicerie et le champ station, 18 pour les employés. Grouper serait plus rapide à écrire et beaucoup plus difficile à déboguer.
| Ajout | Où |
|---|---|
order_board_slots, shelf_slots, stove_count, spice_station_count, les sept statistiques takeout_*, superior_payout, server_count, cook_count | fichier maître, brouillon, valeurs de secours DataCatalog |
Champ station sur les recettes | normalisation Godot et PHP, éditeur JS, tests |
Collection employees | AddressCatalog, Loc.TEXT_FIELDS, miroirs PHP et JS, onglet de l'outil |
Vocabulaires EMPLOYEE_SKILLS, STATION_KINDS | Godot, PHP, JS — comme ROOM_BEHAVIOURS |
| Ardoise et employés embauchés dans la sauvegarde | version 8, sur le modèle des assiettes et des convives |
| Recette, stock, progression et règle X/Y takeout | version 11, avec migration de counter_drinks |
| Textes : postes, compétences, employés, lignes d'ardoise, console | Loc.UI_FALLBACKS puis semis |
Le smoke test couvre aussi le takeout de bout en bout : sélection à la console sans démarrage automatique, cuisson directe du joueur, seuil X et cible Y des cuisiniers, décision physique au comptoir, file séparée, arrivée réelle en tête, délai de base de 30 secondes, bonus joueur et serveur à 1,3× puis 1,6×, absence de bulle de recette, vente sans vaisselle, sérialisation et ventes d'absence.
Il reste deux détails
B1 recette maître : une (pas de mélange dans la réserve)
B2 production : joueur ou cuisinier
B3 service au passant : automatique, selon le débit
B4 refus au comptoir : aucune pénalité
Ces choix sont maintenant construits et couverts par le smoke test. Les réglages d'équilibrage restent dans les sept statistiques takeout_*, sans modifier la boucle.