forked from df-mc/dragonfly
-
Notifications
You must be signed in to change notification settings - Fork 0
/
ender_chest.go
137 lines (116 loc) · 3.76 KB
/
ender_chest.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
package block
import (
"github.com/Adrian8115/dragonfly-Amethyst-Protocol/server/block/cube"
"github.com/Adrian8115/dragonfly-Amethyst-Protocol/server/item"
"github.com/Adrian8115/dragonfly-Amethyst-Protocol/server/item/inventory"
"github.com/Adrian8115/dragonfly-Amethyst-Protocol/server/world"
"github.com/Adrian8115/dragonfly-Amethyst-Protocol/server/world/sound"
"github.com/df-mc/atomic"
"github.com/go-gl/mathgl/mgl64"
)
// enderChestOwner represents an entity that has an ender chest inventory.
type enderChestOwner interface {
ContainerOpener
EnderChestInventory() *inventory.Inventory
}
// EnderChest is a type of chest whose contents are exclusive to each player, and can be accessed from anywhere.
// The empty value of EnderChest is not valid. It must be created using block.NewEnderChest().
type EnderChest struct {
chest
transparent
bass
sourceWaterDisplacer
// Facing is the direction that the ender chest is facing.
Facing cube.Direction
viewers *atomic.Int64
}
// NewEnderChest creates a new initialised ender chest.
func NewEnderChest() EnderChest {
return EnderChest{viewers: atomic.NewInt64(0)}
}
// BreakInfo ...
func (c EnderChest) BreakInfo() BreakInfo {
return newBreakInfo(22.5, pickaxeHarvestable, pickaxeEffective, silkTouchDrop(item.NewStack(Obsidian{}, 8), item.NewStack(NewEnderChest(), 1))).withBlastResistance(3000)
}
// LightEmissionLevel ...
func (c EnderChest) LightEmissionLevel() uint8 {
return 7
}
// SideClosed ...
func (EnderChest) SideClosed(cube.Pos, cube.Pos, *world.World) bool {
return false
}
// UseOnBlock ...
func (c EnderChest) UseOnBlock(pos cube.Pos, face cube.Face, _ mgl64.Vec3, w *world.World, user item.User, ctx *item.UseContext) (used bool) {
pos, _, used = firstReplaceable(w, pos, face, c)
if !used {
return
}
//noinspection GoAssignmentToReceiver
c = NewEnderChest()
c.Facing = user.Rotation().Direction().Opposite()
place(w, pos, c, user, ctx)
return placed(ctx)
}
// Activate ...
func (c EnderChest) Activate(pos cube.Pos, _ cube.Face, _ *world.World, u item.User, _ *item.UseContext) bool {
if opener, ok := u.(enderChestOwner); ok {
opener.OpenBlockContainer(pos)
return true
}
return false
}
// AddViewer ...
func (c EnderChest) AddViewer(w *world.World, pos cube.Pos) {
if c.viewers.Inc() == 1 {
c.open(w, pos)
}
}
// RemoveViewer ...
func (c EnderChest) RemoveViewer(w *world.World, pos cube.Pos) {
if c.viewers.Load() == 0 {
return
}
if c.viewers.Dec() == 0 {
c.close(w, pos)
}
}
// open opens the ender chest, displaying the animation and playing a sound.
func (c EnderChest) open(w *world.World, pos cube.Pos) {
for _, v := range w.Viewers(pos.Vec3()) {
v.ViewBlockAction(pos, OpenAction{})
}
w.PlaySound(pos.Vec3Centre(), sound.EnderChestOpen{})
}
// close closes the ender chest, displaying the animation and playing a sound.
func (c EnderChest) close(w *world.World, pos cube.Pos) {
for _, v := range w.Viewers(pos.Vec3()) {
v.ViewBlockAction(pos, CloseAction{})
}
w.PlaySound(pos.Vec3Centre(), sound.EnderChestClose{})
}
// EncodeNBT ...
func (c EnderChest) EncodeNBT() map[string]interface{} {
return map[string]interface{}{"id": "EnderChest"}
}
// DecodeNBT ...
func (c EnderChest) DecodeNBT(map[string]interface{}) interface{} {
ec := NewEnderChest()
ec.Facing = c.Facing
return ec
}
// EncodeItem ...
func (EnderChest) EncodeItem() (name string, meta int16) {
return "minecraft:ender_chest", 0
}
// EncodeBlock ...
func (c EnderChest) EncodeBlock() (name string, properties map[string]interface{}) {
return "minecraft:ender_chest", map[string]any{"minecraft:cardinal_direction": c.Facing.String()}
}
// allEnderChests ...
func allEnderChests() (chests []world.Block) {
for _, direction := range cube.Directions() {
chests = append(chests, EnderChest{Facing: direction})
}
return
}