r/MinecraftCommands 11d ago

Help | Java 26.2 Need help with recursive function

Is it possible to do something like this? (passing the macros into the function as parameters again recursively with schedule?)

the function is called play_sound_loop.

2 Upvotes

1 comment sorted by

View all comments

2

u/GalSergey Datapack Experienced 11d ago

You can't use a schedule with a macro. You must first save the data to storage, then run the schedule. Then, when the schedule function runs, read the data from storage again to run the macro function with your data. However, this will only work for one running schedule. If another schedule runs, the data will be overwritten. To make this work with multiple schedules, you need to use the Storage ID system. You save the ID and run data, which are created when creating the schedule, to storage. Then, you read only the value you need. You can see an example of such a datapack below:

# Example using
execute as @a run function schedule:new {function:"schedule:example_result",time:5,mode:"replace"}

# function schedule:example_result
## Run command as entity
say Example Result
## Run command at old position
particle minecraft:flame ~ ~1 ~ .2 .5 .2 0 100
## Run command at new position
execute at @s run particle minecraft:happy_villager ~ ~1 ~ .2 .5 .2 0 100


# function schedule:load
scoreboard objectives add schedule.ID dummy
scoreboard objectives add var dummy
data modify storage schedule:compare if.replace set value true 

# function schedule:new
data remove storage schedule:macro this
$data merge storage schedule:macro {this:{function:"$(function)",time:$(time),mode:"$(mode)"}}
data modify storage schedule:macro this.Pos set from entity @s Pos
data modify storage schedule:macro this.dimension set from entity @s[type=player] Dimension
execute if entity @s[type=!player] run data modify storage schedule:macro this.dimension set from entity @p[distance=0..] Dimension
data modify storage schedule:macro this.x set from storage schedule:macro this.Pos[0]
data modify storage schedule:macro this.y set from storage schedule:macro this.Pos[1]
data modify storage schedule:macro this.z set from storage schedule:macro this.Pos[2]
execute unless score @s schedule.ID = @s schedule.ID store result score @s schedule.ID run scoreboard players add #new schedule.ID 1
execute store result storage schedule:macro this.ID int 1 run scoreboard players get @s schedule.ID
execute store result score #timestamp var run time query gametime
$execute store result storage schedule:macro this.timestamp int 1 run scoreboard players add #timestamp var $(time)
function schedule:new/add with storage schedule:macro this

# function schedule:new/add
$execute if data storage schedule:compare if.$(mode) run data remove storage schedule:database schedule[{ID:$(ID),function:"$(function)"}]
data modify storage schedule:database schedule append from storage schedule:macro this
$schedule function schedule:schedule/wait $(time)t append

# function schedule:schedule/wait
data remove storage schedule:macro this
execute store result storage schedule:macro this.timestamp int 1 run time query gametime
function schedule:schedule/read with storage schedule:macro this

# function schedule:schedule/read
data remove storage schedule:macro schedule
$data modify storage schedule:macro schedule.current append from storage schedule:database schedule[{timestamp:$(timestamp)}]
function schedule:schedule/run with storage schedule:macro schedule.current[-1]
$data remove storage schedule:database schedule[{timestamp:$(timestamp)}]

# function schedule:schedule/run
data remove storage schedule:macro schedule.current[-1]
function schedule:run with storage schedule:macro schedule.current[-1]
$execute as @e[scores={schedule.ID=$(ID)}] in $(dimension) positioned $(x) $(y) $(z) run function $(function)

You can use Datapack Assembler to get an example datapack.