Hi,
I am developing a game and I have encountered a problem.
I cannot find the order for the index insertions, it’s been driving me crazy for the last week.
Please, any help is greatly appreciated.
Here is the first snippet :
In this function, the resp.Insert for TITLE works correctly:
func (c *Character) SpawnCharacter() ([]byte, error) {
if c == nil {
return nil, nil
}
if c.Socket == nil || c.Socket.Stats == nil {
return nil, nil
}
resp := CHARACTER_SPAWNED
index := 6
resp.Insert(utils.IntToBytes(uint64(c.PseudoID), 2, true), index) // character pseudo id
index += 2
resp.Insert([]byte{0xee, 0x22, 0x00, 0x00}, index)
index += 4
if c.IsActive {
resp.Insert([]byte{0x03, 0x00, 0x00, 0x00, 0x00}, index)
} else {
resp.Insert([]byte{0x04, 0x00, 0x00, 0x00, 0x00}, index)
}
index += 5
if c.DuelID > 0 {
resp.Overwrite(utils.IntToBytes(500, 2, true), 13) // duel state
}
resp.Insert(utils.IntToBytes(uint64(len(c.Name)), 1, true), index)
index++
resp.Insert([]byte(c.Name), index) // character name
index += len(c.Name)
resp.Insert(utils.IntToBytes(uint64(c.Level), 4, true), index)
index += 4
resp.Insert([]byte{byte(c.Type), byte(c.Class)}, index) // character type-class
index += 2
resp.Insert([]byte{0x01, 0x00, 0x20, 0x1c, 0x00, 0x00, 0x00}, index)
index += 7
coordinate := ConvertPointToLocation(c.Coordinate)
resp.Insert(utils.FloatToBytes(coordinate.X, 4, true), index) // coordinate-x
index += 4
resp.Insert(utils.FloatToBytes(coordinate.Y, 4, true), index) // coordinate-y
index += 4
resp.Insert([]byte{0x00, 0x00, 0x60, 0x41}, index)
index += 4
resp.Insert(utils.FloatToBytes(coordinate.X, 4, true), index) // coordinate-x
index += 4
resp.Insert(utils.FloatToBytes(coordinate.Y, 4, true), index) // coordinate-y
index += 4
resp.Insert([]byte{0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff}, index)
index += 10
resp.Insert(utils.IntToBytes(uint64(c.Socket.Stats.Honor), 4, true), index) // HONOR
index += 4
resp.Insert([]byte{0xc8, 0x00, 0x00, 0x00}, index)
index += 4
resp.Insert(utils.IntToBytes(uint64(c.Socket.Stats.HP), 4, true), index) // hp
index += 4
resp.Insert([]byte{0x00, 0x00, 0x00, 0x00, 0x00}, index)
index += 5
resp.Insert(utils.IntToBytes(uint64(c.WeaponSlot), 1, true), index)
index++
resp.Insert([]byte{0xf2, 0x03}, index)
index += 2
resp.Insert(utils.IntToBytes(uint64(c.BattleMode), 1, true), index) //battle mode
index++
resp.Insert([]byte{0x00, 0x00, 0x05}, index)
index += 3
if c.Morphed {
resp.Insert(utils.IntToBytes(uint64(c.MorphedNPCID), 4, true), index)
index += 4
} else {
resp.Insert([]byte{0x00, 0x00, 0x00, 0x00}, index)
index += 4
}
//index += 5
**resp.Insert(utils.IntToBytes(uint64(c.HonorRank), 4, true), index) // TITLE **
index += 4
resp.Insert(utils.IntToBytes(uint64(c.Type), 1, true), index)
index++
resp.Insert(utils.IntToBytes(uint64(c.GuildID), 4, true), index) // guild id
index += 4
resp.Insert([]byte{0x01, 0x00, 0x00, 0x00}, index)
index += 4
resp.Insert([]byte{byte(c.Faction)}, index) // character faction
index++
resp.Insert([]byte{0x00, 0x00, 0x00, 0x00, 0x64, 0xff, 0xff, 0xff, 0xff}, index)
index += 9
items, err := c.ShowItemsByCharacter()
if err != nil {
return nil, err
}
itemsData := items
sale := FindSale(c.PseudoID)
if sale != nil {
itemsData = []byte{0x05, 0xAA, 0x45, 0xF1, 0x00, 0x00, 0x00, 0xA1, 0x00, 0x00, 0x00, 0x00, 0xB4, 0x6C, 0xF1, 0x00, 0x01, 0x00, 0xA1, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}
}
//myString := hex.EncodeToString(itemsData)
//log.Print("String:", myString)
resp.Insert(itemsData, index)
index += len(itemsData)
if sale != nil {
resp.Insert([]byte{0x02}, index) // sale indicator
index++
resp.Insert([]byte{byte(len(sale.Name))}, index) // sale name length
index++
resp.Insert([]byte(sale.Name), index) // sale name
index += len(sale.Name)
resp.Insert([]byte{0x00}, index)
index++
}
resp.SetLength(int16(binary.Size(resp) - 6))
dataItems, _ := c.ShowItems()
resp.Concat(dataItems) // FIX => workaround for weapon slot
if c.GuildID > 0 {
guild, err := FindGuildByID(c.GuildID)
if err == nil && guild != nil {
resp.Concat(guild.GetInfo())
}
}
STYLE_MENU := utils.Packet{0xaa, 0x55, 0x0d, 0x00, 0x01, 0xb5, 0x0a, 0x00, 0x00, 0x55, 0xaa}
styleresp := STYLE_MENU
styleresp[8] = byte(0x02)
index = 9
headitem, ok := GetItemInfo(c.HeadStyle)
if !ok || headitem == nil {
c.HeadStyle = 0
}
faceitem, ok := GetItemInfo(c.FaceStyle)
if !ok || faceitem == nil {
c.FaceStyle = 0
}
styleresp.Insert(utils.IntToBytes(uint64(c.HeadStyle), 4, true), index)
index += 4
styleresp.Insert(utils.IntToBytes(uint64(c.FaceStyle), 4, true), index)
index += 4
resp.Concat(styleresp)
c.DeleteAura()
return resp, nil
}
However, when I try to implement it in this simplified version, it tells me the order is wrong and the game just bugs out :
func (c *Character) SpawnCharacter() ([]byte, error) {
if c == nil {
return nil, nil
}
resp := CHARACTER_SPAWNED
resp.Insert(utils.IntToBytes(uint64(c.PseudoID), 2, true), 6) // character pseudo id
if c.IsActive {
resp[12] = 3
} else {
resp[12] = 4
}
/*
if c.DuelID > 0 {
resp.Overwrite(utils.IntToBytes(500, 2, true), 13) // duel state
}
*/
resp[17] = byte(len(c.Name)) // character name length
resp.Insert([]byte(c.Name), 18) // character name
index := len(c.Name) + 18 + 4
resp[index] = byte(c.Type) // character type
index += 1
index += 8
coordinate := ConvertPointToLocation(c.Coordinate)
resp.Insert(utils.FloatToBytes(coordinate.X, 4, true), index) // coordinate-x
index += 4
resp.Insert(utils.FloatToBytes(coordinate.Y, 4, true), index) // coordinate-y
index += 8
resp.Insert(utils.FloatToBytes(coordinate.X, 4, true), index) // coordinate-x
index += 4
resp.Insert(utils.FloatToBytes(coordinate.Y, 4, true), index) // coordinate-y
index += 4
index += 18
resp.Overwrite(utils.IntToBytes(uint64(c.Socket.Stats.HP), 4, true), index) // hp
index += 9
resp[index] = byte(c.WeaponSlot) // weapon slot
index += 16
resp.Insert(utils.IntToBytes(uint64(c.GuildID), 4, true), index) // guild id
index += 8
**resp.Insert(utils.IntToBytes(uint64(c.HonorRank), 4, true), index) // TITLE**
index += 4
resp[index] = byte(c.Faction) // character faction
index += 10
items, err := c.ShowItems()
if err != nil {
return nil, err
}
itemsData := items[11 : len(items)-2]
sale := FindSale(c.PseudoID)
if sale != nil {
itemsData = []byte{0x05, 0xAA, 0x45, 0xF1, 0x00, 0x00, 0x00, 0xA1, 0x00, 0x00, 0x00, 0x00, 0xB4, 0x6C, 0xF1, 0x00, 0x01, 0x00, 0xA1, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}
}
resp.Insert(itemsData, index)
index += len(itemsData)
length := int16(len(itemsData) + len(c.Name) + 111)
if sale != nil {
resp.Insert([]byte{0x02}, index) // sale indicator
index++
resp.Insert([]byte{byte(len(sale.Name))}, index) // sale name length
index++
resp.Insert([]byte(sale.Name), index) // sale name
index += len(sale.Name)
resp.Insert([]byte{0x00}, index)
index++
length += int16(len(sale.Name) + 3)
}
resp.SetLength(length)
resp.Concat(items) // FIX => workaround for weapon slot
if c.GuildID > 0 {
guild, err := FindGuildByID(c.GuildID)
if err == nil && guild != nil {
resp.Concat(guild.GetInfo())
}
}
return resp, nil
}