CommandBlock Tutoriel Détecter l'heure RÉELLE dans minecraft! -1.9-

Eglaios

Crétin de la commu
14 Avril 2018
310
42
89
25
-EDIT : marche pour toutes les versions suivantes!! Et avec les spoilers, c'est bien mieux!-
Vous avez toujours voulu créer un événement nocturne dans minecraft? Une interaction avec un villageois qui donnerait au joueur, à 15h59, une clé secrète, et tout cela en vanilla 1.9? Impossible!

...En fait, non.
Croyez-le ou non, ces rêves deviendront réalité grâce à un petit système fait maison qui vous permettra de les reproduire dans vos propres maps! (Cette version-ci est en 1.9.4, mais elle doit sans doute pouvoir être faite dans d'autres versions)

L'idée m'est venue d'une fonctionnalité relativement peu utile des blocs de commande : la ligne "Résultat précédent".
Son rôle est d'afficher, comme son nom l'indique, un retour sur la dernière commande exécutée par le bloc en question.

Parties :
-Le principe
-La structure et les commandes
-Inconvénients et solutions



Le principe
Etape 1 : Obtenir l'heure

Il suffit de faire exécuter à répétition une commande à résultat fixe. Pour cette petite structure, j'ai utilisé la commande "/gamerule doFireTick". (Le système s'attend à ce que celle-ci soit mise en "false", c'est généralement le cas de beaucoup de maps).
Le résultat du bloc de commande affichera donc toujours la même chose, que la gamerule est sur false.

La même chose? Pas tout à fait! Voici précisément ce que le bloc de commande renvoie :
Code:
[14:55:07] doFireTick = false
Eh oui, le bloc a été exécuté pour la dernière fois à 14 heures 55 minutes et 7 secondes! Les choses s'éclaircissent!


Etape 2 : Détecter l'heure obtenue

Maintenant que le bloc de commande affiche l'heure exacte, il faut réussir à la détecter. Comment? Avec la commande /testforblock (Toujours en 1.9, évidemment)!
En regardant le bloc de /gamerule avec le /blockdata, voici ce qui est affiché :

2019-03-05_15.11.42.png

Ce qui nous intéresse, c'est l'argument "LastOutput", commençant à la troisième ligne pour finir à la dernière. C'est donc la partie la plus énervante; copier tout le json et ne pas oublier ces maudits espaces avant et après l'heure et le "\u003d" (Unicode du symbole "=") :'(

Enfin, on en tire la commande qui permet de détecter l'heure :
Code:
/testforblock ~ ~-2 ~ minecraft:repeating_command_block 1 {LastOutput:"{\"extra\":[{\"extra\":[{\"text\":\" \u003d \"},{\"text\":\"false\"}],\"text\":\"doFireTick\"}],\"text\":\"[15:11:22] \"}"}

Et voilà! C'est... pas encore parfait, vu qu'il faudra attendre 24 heures plus tard pour voir le système se déclencher... Il faudra donc régler le /testforblock à l'heure désirée. Pour cela, il suffit de changer l'heure présente dans la commande ci-dessus (par exemple, changer le [15:11:22] pour [20:00:00] si l'a structure doit s'activer à 20 heures).

La structure
2019-03-05_14.18.45.png


Blocs de commande :

1 : Impulsion - inconditionnel - par la redstone
Rôle : Désactivation de la propagation du feu - À activer une fois, indispensable, peut être détruit après
Code:
/gamerule doFireTick false
2 : Répétition - inconditionnel - toujours actif
Rôle : Actualisation de l'heure réelle dans le jeu - À pointer vers le haut
Code:
/gamerule doFireTick
3 : Répétition - inconditionnel - toujours actif
Rôle : Détection de l'heure sélectionnée - Remplacer [14:22:50] par l'heure voulue (heure-minute-seconde), à placer 2 blocs au-dessus du bloc #2 comme sur l'image, NE PAS SUPPRIMER L'ESPACE APRÈS [14:22:50] !
Code:
/testforblock ~ ~-2 ~ minecraft:repeating_command_block 1 {LastOutput:"{\"extra\":[{\"extra\":[{\"text\":\" \u003d \"},{\"text\":\"false\"}],\"text\":\"doFireTick\"}],\"text\":\"[14:22:50] \"}"}
4 : Bloc de commande en chaîne, pour répéter une action pendant la seconde d'activation. Commande non spécifiée.

Inconvénients du système et moyens de les contourner (IMPORTANT, À LIRE!!!)
1. Problème : Le bloc de /testforblock est activé pendant une seconde
Comme le bloc de /gamerule s'actualise toutes les secondes, lorsque le bloc de /testforblock sera exécuté avec succès, si un bloc de commande en chaîne y est connecté, il sera activé une dizaine de fois dans la seconde! Pour un système de détection, c'est pratique, mais pour une série de commandes, avec du /give, par exemple, ça peut être très problématique
Solution : Mettre un comparateur pour ne déclencher qu'une fois

2. Problème : Le bloc de /testforblock ne peut QUE s'activer pendant une seconde, ni plus ni moins.

Le système ne peut détecter qu'une heure précise, pas d'intervalle (du moins, à ce que je sache), le temps affiché étant un texte et non pas une variable!
Solution : Mettre deux blocs de /testforblock!
S'il faut activer un système pendant un intervalle, il suffit de mettre deux blocs de /testforblock : un qui se déclenchera le premier, activant le système, et un autre bloc se déclenchant plus tard, qui désactivera le système!
-CORRECTION- CE SYSTÈME COMPORTE TROP DE FAILLES POUR ÊTRE ADOPTE : LE JOUEUR EST OBLIGE D'ETRE PRESENT AUX DEUX MOMENTS SANS QUOI LA DUREE EST ALTEREE. Il faudra perfectionner tout ça pour tenter de résoudre ce problème d'une autre façon.


3. Problème : Le temps réel continue quand minecraft est mis en pause (ah bon :confused:)

Eh oui, on ne peut pas arrêter le temps, et ça cause un certain problème : Si jamais la structure doit s'activer à 20h et qu'entre 19h59 et 20h01, le joueur avait mis son jeu en pause, les données du block de /gamerule passeront de [19:59:00] à [20:01:00]! L'activation n'aura donc pas eu lieu et il aurait fallu attendre le jour suivant! (Ou changer l'heure de l'ordinateur, mais chuuuut! :fou: )
Solution : Mettre en multijoueur
En multijoueur, ouvrir le menu ne met pas le jeu en pause! Petit hic : il existe une commande pour mettre automatiquement un monde en LAN, le /publish, mais elle est inutilisable en bloc de commande, est même en clickEvent de tellraw, de livre ou de pancarte (Oui, j'ai TOUT essayé). Donc soit régler ce problème est capital (Surtout avec la solution du problème #2, les petits malins sauteraient le bloc de désactivation :fou:), et dans ce cas, mieux vaut mettre un système d'avertissement au joueur pour lui dire d'ouvrir le monde en LAN manuellement, soit ce n'est pas grave et c'est mieux de rester avec ce problème plus ou moins important, ça dépend de vous!


J'espère que vous saurez tirer parti de ce système amusant (Peut-être un peu frustrant?) tout à fait exclusif, je n'ai rien trouvé de tel sur internet. Amusez-vous bien!



Eglaios
 
Dernière édition:
Petit update : J'ai vraiment cherché un moyen de pouvoir actualiser l'heure réelle à chaque tick, j'ai donc fait quelques recherches et trouvé tous les tags de command blocks :
Données de l'entité de bloc
  • Tous les tags communs aux entités de bloc [masquer]

  • id : Identifiant de l'entité de bloc. Cet identifiant peut ne pas être le même que celui du bloc lui-même.

  • x : Coordonnée X de l'entité de bloc.

  • y : Coordonnée Y de l'entité de bloc.

  • z : Coordonnée Z de l'entité de bloc.

  • CustomName : Optionnel. Un nom personnalisé qui sera stocké et qui remplacera le "@" habituel dans des commandes telles que /say ou /tell.

  • Command : La commande enregistrée dans le bloc de commande.

  • SuccessCount : Représente la puissance du signal analogique émis par les comparateurs de redstoneattachés à ce wagonnet. Mise à jour uniquement lorsque le wagonnet est activé avec des rails déclencheurs.

  • LastOutput : La dernière ligne de sortie générée par le wagonnet. Toujours stocké même si la règle de jeu /gamerule commandBlockOutput est définie sur faux. Apparaît dans l'interface graphique du wagonnet lorsque vous faites un clic droit et inclut un horodatage de la sortie.

  • TrackOutput : 1 ou 0 (vrai/faux) - Détermine si le LastOutput sera ou non stocké. Peut être activé dans l'interface graphique en cliquant sur un bouton situé près de la zone de texte "Résultat précédent". La légende sur le bouton indique l'état actuel : "O" si vrai, "X" si faux.

  • powered : 1 ou 0 (vrai/faux) - Indique si le bloc de commande est alimenté ou non par de la redstone.

  • auto : 1 ou 0 (vrai/faux) - Permet d'activer la commande sans avoir besoin d'un signal de redstone.

  • conditionMet : 1 ou 0 (vrai/faux) - Indique si la condition d'un bloc de commande conditionnel a été remplie lors de la dernière activation. Vrai si ce n'est pas un bloc de commande conditionnel.

  • UpdateLastExecution : 1 ou 0 (vrai/faux) - Par défaut à vrai. Si la valeur est fausse, des boucles peuvent être créées, et le même bloc de commande peut s'exécuter plusieurs fois en un tick.

  • LastExecution : Tick de la dernière exécution de la commande.
Source : minecraft wiki
L'heure définie se trouve dans "LastOutput" qui est un tag au format JSON, donc impossible à traduire dans un score ou autre

Cependant, LastExecution est très pratique pour obtenir les ticks depuis la création de la map avec, par exemple, un simple :
Code:
/execute store result score @p time run data get block ~ ~-1 ~ LastExecution
Je me suis donc détourné des tags de blocs de commande pour chercher ailleurs un moyen d'obtenir l'heure réelle plus précis. En fait, il y a un mot pour ça : le Timestamp...

J'ai vu que le timestamp se trouvait dans plusieurs fichiers différents du jeu, mais je ne sais pas pour l'instant comment l'en extraire... Si vous avez des idées pour y parvenir, n'hésitez pas!
 
  • J'aime
Reactions: FunkyToc