Add 1.21.20

This commit is contained in:
AkmalFairuz
2025-01-01 12:34:03 +07:00
parent 93821ab4c6
commit 9677eef999
19 changed files with 7267 additions and 60 deletions

View File

@@ -0,0 +1,58 @@
package proto
import "github.com/sandertv/gophertunnel/minecraft/protocol"
// Attribute is an entity attribute, that holds specific data such as the health of the entity. Each attribute
// holds a default value, maximum and minimum value, name and its current value.
type Attribute struct {
protocol.AttributeValue
// DefaultMin is the default minimum value of the attribute. It's not clear why this field must be sent to
// the client, but it is required regardless.
DefaultMin float32
// DefaultMax is the default maximum value of the attribute. It's not clear why this field must be sent to
// the client, but it is required regardless.
DefaultMax float32
// Default is the default value of the attribute. It's not clear why this field must be sent to the
// client, but it is required regardless.
Default float32
// Modifiers is a slice of AttributeModifiers that are applied to the attribute.
Modifiers []protocol.AttributeModifier
}
func (x *Attribute) FromLatest(v protocol.Attribute) Attribute {
x.AttributeValue = v.AttributeValue
x.DefaultMin = v.DefaultMin
x.DefaultMax = v.DefaultMax
x.Default = v.Default
x.Modifiers = v.Modifiers
return *x
}
func (x *Attribute) ToLatest() protocol.Attribute {
return protocol.Attribute{
AttributeValue: protocol.AttributeValue{
Name: x.Name,
Value: x.Value,
Max: x.Max,
Min: x.Min,
},
DefaultMin: x.DefaultMin,
DefaultMax: x.DefaultMax,
Default: x.Default,
Modifiers: x.Modifiers,
}
}
// Marshal encodes/decodes an Attribute.
func (x *Attribute) Marshal(r protocol.IO) {
r.Float32(&x.Min)
r.Float32(&x.Max)
r.Float32(&x.Value)
if IsProtoGTE(r, ID729) {
r.Float32(&x.DefaultMin)
r.Float32(&x.DefaultMax)
}
r.Float32(&x.Default)
r.String(&x.Name)
protocol.Slice(r, &x.Modifiers)
}

View File

@@ -53,7 +53,7 @@ type CameraPreset struct {
AimAssist protocol.Optional[protocol.CameraPresetAimAssist]
}
func (x *CameraPreset) FromLatest(cp protocol.CameraPreset) {
func (x *CameraPreset) FromLatest(cp protocol.CameraPreset) CameraPreset {
x.Name = cp.Name
x.Parent = cp.Parent
x.PosX = cp.PosX
@@ -74,6 +74,7 @@ func (x *CameraPreset) FromLatest(cp protocol.CameraPreset) {
x.PlayerEffects = cp.PlayerEffects
x.AlignTargetAndCameraForward = cp.AlignTargetAndCameraForward
x.AimAssist = cp.AimAssist
return *x
}
func (x *CameraPreset) ToLatest() protocol.CameraPreset {
@@ -110,8 +111,10 @@ func (x *CameraPreset) Marshal(r protocol.IO) {
protocol.OptionalFunc(r, &x.PosZ, r.Float32)
protocol.OptionalFunc(r, &x.RotX, r.Float32)
protocol.OptionalFunc(r, &x.RotY, r.Float32)
protocol.OptionalFunc(r, &x.RotationSpeed, r.Float32)
protocol.OptionalFunc(r, &x.SnapToTarget, r.Bool)
if IsProtoGTE(r, ID729) {
protocol.OptionalFunc(r, &x.RotationSpeed, r.Float32)
protocol.OptionalFunc(r, &x.SnapToTarget, r.Bool)
}
if IsProtoGTE(r, ID748) {
protocol.OptionalFunc(r, &x.HorizontalRotationLimit, r.Vec2)
protocol.OptionalFunc(r, &x.VerticalRotationLimit, r.Vec2)
@@ -121,7 +124,9 @@ func (x *CameraPreset) Marshal(r protocol.IO) {
protocol.OptionalFunc(r, &x.TrackingRadius, r.Float32)
}
protocol.OptionalFunc(r, &x.ViewOffset, r.Vec2)
protocol.OptionalFunc(r, &x.EntityOffset, r.Vec3)
if IsProtoGTE(r, ID729) {
protocol.OptionalFunc(r, &x.EntityOffset, r.Vec3)
}
protocol.OptionalFunc(r, &x.Radius, r.Float32)
protocol.OptionalFunc(r, &x.AudioListener, r.Uint8)
protocol.OptionalFunc(r, &x.PlayerEffects, r.Bool)

View File

@@ -0,0 +1,38 @@
package proto
import "github.com/sandertv/gophertunnel/minecraft/protocol"
// FullContainerName contains information required to identify a container in a StackRequestSlotInfo.
type FullContainerName struct {
// ContainerID is the ID of the container that the slot was in.
ContainerID byte
// DynamicContainerID is the ID of the container if it is dynamic. If the container is not dynamic, this
// field should be left empty. A non-optional value of 0 is assumed to be non-empty.
DynamicContainerID protocol.Optional[uint32]
}
func (x *FullContainerName) FromLatest(v protocol.FullContainerName) FullContainerName {
x.ContainerID = v.ContainerID
x.DynamicContainerID = v.DynamicContainerID
return *x
}
func (x *FullContainerName) ToLatest() protocol.FullContainerName {
return protocol.FullContainerName{
ContainerID: x.ContainerID,
DynamicContainerID: x.DynamicContainerID,
}
}
func (x *FullContainerName) Marshal(r protocol.IO) {
r.Uint8(&x.ContainerID)
if IsProtoGTE(r, ID729) {
protocol.OptionalFunc(r, &x.DynamicContainerID, r.Uint32)
} else {
dynamicContainerID, _ := x.DynamicContainerID.Value()
r.Uint32(&dynamicContainerID)
if dynamicContainerID != 0 {
x.DynamicContainerID = protocol.Option(dynamicContainerID)
}
}
}

View File

@@ -3,12 +3,12 @@ package proto
import "github.com/sandertv/gophertunnel/minecraft/protocol"
const (
ID766 = 766
ID748 = 748
ID729 = 729
ID712 = 712
ID686 = 686
ID685 = 685
ID766 = 766 // v1.21.50
ID748 = 748 // v1.21.40
ID729 = 729 // v1.21.30
ID712 = 712 // v1.21.20
ID686 = 686 // v1.21.2
ID685 = 685 // v1.21.0
)
func IsProtoGTE(io protocol.IO, proto int32) bool {

View File

@@ -226,6 +226,32 @@ type ItemStackResponse struct {
ContainerInfo []StackResponseContainerInfo
}
func (x *ItemStackResponse) FromLatest(y protocol.ItemStackResponse) ItemStackResponse {
ret := ItemStackResponse{
Status: y.Status,
RequestID: y.RequestID,
ContainerInfo: make([]StackResponseContainerInfo, len(y.ContainerInfo)),
}
for i, v := range y.ContainerInfo {
ret.ContainerInfo[i] = StackResponseContainerInfo{
Container: (&FullContainerName{}).FromLatest(v.Container),
SlotInfo: make([]StackResponseSlotInfo, len(v.SlotInfo)),
}
for j, w := range v.SlotInfo {
ret.ContainerInfo[i].SlotInfo[j] = StackResponseSlotInfo{
Slot: w.Slot,
HotbarSlot: w.HotbarSlot,
Count: w.Count,
StackNetworkID: w.StackNetworkID,
CustomName: w.CustomName,
FilteredCustomName: w.FilteredCustomName,
DurabilityCorrection: w.DurabilityCorrection,
}
}
}
return ret
}
func (x *ItemStackResponse) ToLatest() protocol.ItemStackResponse {
ret := protocol.ItemStackResponse{
Status: x.Status,
@@ -234,7 +260,7 @@ func (x *ItemStackResponse) ToLatest() protocol.ItemStackResponse {
}
for i, v := range x.ContainerInfo {
ret.ContainerInfo[i] = protocol.StackResponseContainerInfo{
Container: v.Container,
Container: v.Container.ToLatest(),
SlotInfo: make([]protocol.StackResponseSlotInfo, len(v.SlotInfo)),
}
for j, w := range v.SlotInfo {
@@ -266,7 +292,7 @@ type StackResponseContainerInfo struct {
// Container is the FullContainerName that describes the container that the slots that follow are in. For
// the main inventory, the ContainerID seems to be 0x1b. Fur the cursor, this value seems to be 0x3a. For
// the crafting grid, this value seems to be 0x0d.
Container protocol.FullContainerName
Container FullContainerName
// SlotInfo holds information on what item stack should be present in specific slots in the container.
SlotInfo []StackResponseSlotInfo
}
@@ -635,7 +661,7 @@ func (a *CraftResultsDeprecatedStackRequestAction) Marshal(r protocol.IO) {
// StackRequestSlotInfo holds information on a specific slot client-side.
type StackRequestSlotInfo struct {
// Container is the FullContainerName that describes the container that the slot is in.
Container protocol.FullContainerName
Container FullContainerName
// Slot is the index of the slot within the container with the ContainerID above.
Slot byte
// StackNetworkID is the unique stack ID that the client assumes to be present in this slot. The server

View File

@@ -38,6 +38,20 @@ type TexturePackInfo struct {
DownloadURL string
}
func (x *TexturePackInfo) FromLatest(y protocol.TexturePackInfo) TexturePackInfo {
x.UUID = y.UUID
x.Version = y.Version
x.Size = y.Size
x.ContentKey = y.ContentKey
x.SubPackName = y.SubPackName
x.ContentIdentity = y.ContentIdentity
x.HasScripts = y.HasScripts
x.AddonPack = y.AddonPack
x.RTXEnabled = y.RTXEnabled
x.DownloadURL = y.DownloadURL
return *x
}
func (x *TexturePackInfo) ToLatest() protocol.TexturePackInfo {
return protocol.TexturePackInfo{
UUID: x.UUID,
@@ -79,3 +93,42 @@ func (x *TexturePackInfo) Marshal(r protocol.IO) {
r.String(&x.DownloadURL)
}
}
// BehaviourPackInfo represents a behaviour pack's info sent over network. It holds information about the
// behaviour pack such as its name, description and version.
type BehaviourPackInfo struct {
// UUID is the UUID of the behaviour pack. Each behaviour pack downloaded must have a different UUID in
// order for the client to be able to handle them properly.
UUID string
// Version is the version of the behaviour pack. The client will cache behaviour packs sent by the server as
// long as they carry the same version. Sending a behaviour pack with a different version than previously
// will force the client to re-download it.
Version string
// Size is the total size in bytes that the behaviour pack occupies. This is the size of the compressed
// archive (zip) of the behaviour pack.
Size uint64
// ContentKey is the key used to decrypt the behaviour pack if it is encrypted. This is generally the case
// for marketplace behaviour packs.
ContentKey string
// SubPackName ...
SubPackName string
// ContentIdentity ...
ContentIdentity string
// HasScripts specifies if the behaviour packs has any scripts in it. A client will only download the
// behaviour pack if it supports scripts, which, up to 1.11, only includes Windows 10.
HasScripts bool
// AddonPack specifies if the texture pack is from an addon.
AddonPack bool
}
// Marshal encodes/decodes a BehaviourPackInfo.
func (x *BehaviourPackInfo) Marshal(r protocol.IO) {
r.String(&x.UUID)
r.String(&x.Version)
r.Uint64(&x.Size)
r.String(&x.ContentKey)
r.String(&x.SubPackName)
r.String(&x.ContentIdentity)
r.Bool(&x.HasScripts)
r.Bool(&x.AddonPack)
}