Copying the item into the player's inventory
This is aA great way to actually modify the item in the player’s inventorypost has already been made regarding this:
How can I modify an item while it is inside the player's inventory?
Setting the lodestone position
As far as changing the compass NBT goes, thisThese should suffice:
Now, why does this work?
I’m on mobile so I can’t test this atThe player's Pos attribute is an array of doubles (high-precision decimal values), whereas the momentcompass's LodestonePos is an Object with attributes X, Y, and Z, which are all ints (whole numbers between -231 and 231-1).
Why the developers decided to have different implementations of coordinates is beyond me, but I hopewhat this means for us is that we have to make three seperate assignments; one for each axis.
First, we get the player's position
Let's use @p for simplicity
data get @p Pos
this will return something like [0d, 3.14d, 12345.678d], which is an array of the X, Y, and Z coordinates respectively.
data get @p Pos[0]
This is just the X coordinate
Now let's store a value into an item
Let's use 0 0 0 as the location of a shulker box with a single compass in it works
execute store result block 0 0 0 Items[0].LodestonePos.X ...
This is accessing the X coordinate of the LodestonePos attribute of the first item in a shulker box at 0 0 0, presuming one exists.
breaking down the execute command
Now we have
execute store result block <shucker box coords> Items[0].LodestonePos.X int 1 run data get entity @p[<however you’re selecting the runner>] Pos[0]
which will store the player's x position into the lodestone compass's X attribute.
Let's look at it piece by piece
# using the 'store' directive indicates you want to put a value somewhere
execute store
# you want to store the value you get, not just whether-or-not it succeeds
result
# you want to put the result into a TileEntity (aka Block Entity) like a chest or shulker box
block
#the location of the tile entity
0 0 0
# the NBT path of the tile entity you want to edit
Items[0].LodestonePos.X
# indicates the resulting value should be converted to type `int`
int
# the scale of the resulting value (just multiplication)
1
# you want to run a command to get a value
run
# the command that should return the desired value
data get entity @p[<however you’re selecting the runner>]
Making it work for X, Y, and Z
This is relatively simple. Just replace Pos[0] with Pos[1] for the Y-coodinate, or Pos[2] for the Z-coordinate.
Then Replace LodestonePos.X with LodestonePos.Y and LodestonePos.Z, and there you! have the 3 different commands