183 lines
3.6 KiB
Go
183 lines
3.6 KiB
Go
package main
|
|
|
|
import (
|
|
"bytes"
|
|
"encoding/binary"
|
|
"io"
|
|
"log"
|
|
|
|
"github.com/anon55555/mt/rudp"
|
|
)
|
|
|
|
const (
|
|
AoCmdSetProps = iota
|
|
AoCmdUpdatePos
|
|
AoCmdSetTextureMod
|
|
AoCmdSetSprite
|
|
AoCmdPunched
|
|
AoCmdUpdateArmorGroups
|
|
AoCmdSetAnimation
|
|
AoCmdSetBonePos
|
|
AoCmdAttachTo
|
|
AoCmdSetPhysicsOverride
|
|
AoCmdObsolete1
|
|
AoCmdSpawnInfant
|
|
AoCmdSetAnimSpeed
|
|
)
|
|
|
|
func processAoRmAdd(c *Conn, r *bytes.Reader) []byte {
|
|
w := &bytes.Buffer{}
|
|
|
|
countRm := ReadUint16(r)
|
|
WriteUint16(w, countRm)
|
|
|
|
var aoRm []uint16
|
|
for i := uint16(0); i < countRm; i++ {
|
|
id := ReadUint16(r)
|
|
|
|
if id == c.localPlayerCao {
|
|
id = c.currentPlayerCao
|
|
}
|
|
|
|
WriteUint16(w, id)
|
|
aoRm = append(aoRm, id)
|
|
}
|
|
|
|
countAdd := ReadUint16(r)
|
|
WriteUint16(w, countAdd)
|
|
|
|
var aoAdd []uint16
|
|
for i := uint16(0); i < countAdd; i++ {
|
|
id := ReadUint16(r)
|
|
objType := ReadUint8(r)
|
|
initData := ReadBytes32(r)
|
|
|
|
dr := bytes.NewReader(initData)
|
|
dr.Seek(1, io.SeekStart)
|
|
|
|
name := string(ReadBytes16(dr))
|
|
|
|
if name == c.Username() {
|
|
if c.initAoReceived {
|
|
// Read the messages from the packet
|
|
// They need to be forwarded
|
|
dr.Seek(30, io.SeekCurrent)
|
|
|
|
msgcountByte, _ := dr.ReadByte()
|
|
msgcount := uint8(msgcountByte)
|
|
|
|
var msgs [][]byte
|
|
for j := uint8(0); j < msgcount; j++ {
|
|
dr.Seek(2, io.SeekCurrent)
|
|
|
|
msglenBytes := make([]byte, 2)
|
|
dr.Read(msglenBytes)
|
|
msglen := binary.BigEndian.Uint16(msglenBytes)
|
|
|
|
msg := make([]byte, msglen)
|
|
dr.Read(msg)
|
|
|
|
msgs = append(msgs, msg)
|
|
}
|
|
|
|
// Generate message packet
|
|
msgpkt := []byte{0x00, ToClientActiveObjectMessages}
|
|
for _, msg := range msgs {
|
|
msgdata := make([]byte, 4+len(msg))
|
|
binary.BigEndian.PutUint16(msgdata[0:2], c.localPlayerCao)
|
|
binary.BigEndian.PutUint16(msgdata[2:4], uint16(len(msg)))
|
|
copy(msgdata[4:], aoMsgReplaceIDs(c, msg))
|
|
msgpkt = append(msgpkt, msgdata...)
|
|
}
|
|
|
|
ack, err := c.Send(rudp.Pkt{Reader: bytes.NewReader(msgpkt)})
|
|
if err != nil {
|
|
log.Print(err)
|
|
}
|
|
<-ack
|
|
|
|
data := w.Bytes()
|
|
binary.BigEndian.PutUint16(data[4+countRm*2:6+countRm*2], countAdd-1)
|
|
w = bytes.NewBuffer(data)
|
|
|
|
c.currentPlayerCao = id
|
|
continue
|
|
} else {
|
|
c.initAoReceived = true
|
|
c.localPlayerCao = id
|
|
c.currentPlayerCao = id
|
|
}
|
|
} else if id == c.localPlayerCao {
|
|
id = c.currentPlayerCao
|
|
}
|
|
|
|
if name != c.Username() {
|
|
aoAdd = append(aoAdd, id)
|
|
}
|
|
|
|
WriteUint16(w, id)
|
|
WriteUint8(w, objType)
|
|
WriteBytes32(w, initData)
|
|
}
|
|
|
|
c.redirectMu.Lock()
|
|
for i := range aoAdd {
|
|
if aoAdd[i] != 0 {
|
|
c.aoIDs[aoAdd[i]] = true
|
|
}
|
|
}
|
|
|
|
for i := range aoRm {
|
|
c.aoIDs[aoRm[i]] = false
|
|
}
|
|
c.redirectMu.Unlock()
|
|
|
|
return w.Bytes()
|
|
}
|
|
|
|
func processAoMsgs(c *Conn, r *bytes.Reader) []byte {
|
|
w := &bytes.Buffer{}
|
|
|
|
for r.Len() >= 4 {
|
|
id := ReadUint16(r)
|
|
|
|
msg := aoMsgReplaceIDs(c, ReadBytes16(r))
|
|
|
|
if id == c.currentPlayerCao {
|
|
id = c.localPlayerCao
|
|
} else if id == c.localPlayerCao {
|
|
id = c.currentPlayerCao
|
|
}
|
|
|
|
WriteUint16(w, id)
|
|
WriteBytes16(w, msg)
|
|
}
|
|
|
|
return w.Bytes()
|
|
}
|
|
|
|
func aoMsgReplaceIDs(c *Conn, data []byte) []byte {
|
|
switch cmd := data[0]; cmd {
|
|
case AoCmdAttachTo:
|
|
id := binary.BigEndian.Uint16(data[1:3])
|
|
if id == c.currentPlayerCao {
|
|
id = c.localPlayerCao
|
|
binary.BigEndian.PutUint16(data[1:3], id)
|
|
} else if id == c.localPlayerCao {
|
|
id = c.currentPlayerCao
|
|
binary.BigEndian.PutUint16(data[1:3], id)
|
|
}
|
|
case AoCmdSpawnInfant:
|
|
id := binary.BigEndian.Uint16(data[1:3])
|
|
if id == c.currentPlayerCao {
|
|
id = c.localPlayerCao
|
|
binary.BigEndian.PutUint16(data[1:3], id)
|
|
} else if id == c.localPlayerCao {
|
|
id = c.currentPlayerCao
|
|
binary.BigEndian.PutUint16(data[1:3], id)
|
|
}
|
|
}
|
|
|
|
return data
|
|
}
|