View difference between Paste ID: nqkTWRt4 and n7VUxLiy
SHOW: | | - or go back to the newest paste.
1-
pastebin/gist
1+
import net, json, strutils, sequtils, sugar, PlayerInput
2
3
4
type Bot* = object
5
    name*: string
6
    rootsocket*: Socket
7
    inputs*: PlayerInputs
8
9
10
proc tojson(inputs: PlayerInputs): JsonNode =
11
    ## Quick wrapper around the generic JObject constructor.
12
    result = %[("steer", %inputs.steer), 
13
    ("throttle", %inputs.throttle), 
14
    ("roll", %inputs.roll), 
15
    ("pitch", %inputs.pitch), 
16
    ("yaw", %inputs.yaw), 
17
    ("jump", %inputs.jump), 
18
    ("boost", %inputs.boost), 
19
    ("use_item", %inputs.use_item), 
20
    ("chat", %inputs.chat)]
21
22
23
proc unrollBytes(n : uint16) : string =
24
    let shifts : seq[uint16] = @[0'u16, 8'u16]
25
    # shift each byte right by a certain amount and mask off the least-significant byte
26
    map(shifts, shift => $char((n shr shift) and 0x000000ff)).join
27
    
28
    
29
proc rollBytes(bs : string) : uint16 =
30
    let shifts : seq[uint16] = @[0'u16, 8'u16]
31
    var n : uint16
32
    for pair in zip(shifts, bs):
33
        n = n or pair.b.uint16 shl pair.a
34
    return n
35
36
proc try_connect(bot: Bot, add: string = "localhost", port: Port) =
37
    bot.rootsocket.connect(add, port)
38
    echo("Bot: ", bot.name, " connected to server on address: localhost, on port: ", port)
39
40
proc get_inputs(inputs: var PlayerInputs, game_info: JsonNode) =
41
    var 
42
        steer: float = 0.0
43
        throttle: float = 0.0
44
        roll: float = 0.0
45
        pitch: float = 0.0
46
        yaw: float = 0.0
47
        jump: bool = false
48
        boost: bool = false
49
        use_item: bool = false
50
        chat: int = 0
51
52
    inputs = PlayerInputs(steer: steer, 
53
                    throttle: throttle, 
54
                    roll: roll, 
55
                    pitch: pitch, 
56
                    yaw: yaw, 
57
                    jump: jump, 
58
                    boost: boost, 
59
                    use_item: use_item, 
60
                    chat: chat) 
61
62
proc recievePacket(bot: Bot): JsonNode =
63
    var recieved: string = bot.rootsocket.recv(1024)
64
    #echo(recieved, "     |     ", recieved[2..^1], "     |     ", rollBytes(recieved[2..^2]), "     |     ", recieved.toHex()[2..3], recieved.toHex()[0..1])
65
    #var full_length: int = len("""[{"type":"Game","frame":0,"score":[0,0],"ball":{"position":[0.0,0.0,0.0],"velocity":[0.0,0.0,0.0],"euler_angles":[0.0,0.0,0.0],"angular_velocity":[0.0,0.0,0.0],"damage":0.0,"shape":0,"radius":-1.0,"height":-1.0},"cars":[{"position":[0.0,0.0,0.0],"velocity":[0.0,0.0,0.0],"euler_angles":[0.0,0.0,0.0],"angular_velocity":[0.0,0.0,0.0],"boost":0.0,"on_ground":true,"jumped":false,"double_jumped":false,"demolished":false,"is_bot":true,"team":-1,"name":"","body_type":0,"hitbox_offset":[0.0,0.0,0.0],"hitbox_dimensions":[0.0,0.0,0.0]},{"position":[0.0,0.0,0.0],"velocity":[0.0,0.0,0.0],"euler_angles":[0.0,0.0,0.0],"angular_velocity":[0.0,0.0,0.0],"boost":0.0,"on_ground":true,"jumped":false,"double_jumped":false,"demolished":false,"is_bot":true,"team":-1,"name":"","body_type":0,"hitbox_offset":[0.0,0.0,0.0],"hitbox_dimensions":[0.0,0.0,0.0]}],"goals":[],"pads":[],"time_left":0.0,"time_elapsed":0.0,"is_overtime":true,"is_round_active":true,"is_kickoff_paused":false,"is_match_ended":false,"is_unlimited_time":false,"gravity":0.0,"map":0,"mode":0}]""")
66
    let header: uint16 = rollBytes(recieved[0..2])
67
    recieved = recieved[2..^1]
68
    #echo(full_length, ", ", header, ", ", len(recieved).uint16)
69
    #echo("reciving data...  data recived so far: ", len(recived), "  data to recive: ", fromHex[int16](header), " collecting: ", fromHex[int16](header) - len(recived) - 4, " bytes")
70
    recieved.add(bot.rootsocket.recv(header.int - len(recieved)))#((header2.parseHexInt() - len(recieved)) - 1))
71
72
    let packet: JsonNode = json.parseJson("{\"Game\":" & recieved & "}")
73
    echo("data recived: ")
74
    echo(packet)
75
    return packet
76
77
78
var Mybot: Bot = Bot(name: "Nimbot")
79
var port: Port = Port(8085)
80
Mybot.rootsocket = newSocket(AF_INET, SOCK_STREAM)
81
MyBot.inputs = PlayerInputs(steer: 0.0, 
82
                            throttle: 0.0, 
83
                            roll: 0.0, 
84
                            pitch: 0.0, 
85
                            yaw: 0.0, 
86
                            jump: false, 
87
                            boost: false, 
88
                            use_item: false, 
89
                            chat: 0)
90
91
92
proc send_inputs(bot: Bot, game_info: JsonNode) =
93
    var inputs = bot.inputs
94
    inputs.get_inputs(game_info)
95
    let strinputs: string = $tojson(inputs)
96
    let header: string = (strinputs.len + 2).uint16.unrollBytes
97
    let buffer: string = header & strinputs
98
    echo(buffer, "    |    ", len(strinputs), "    |    ", header, "    |    ")
99
    bot.rootsocket.send(buffer)
100
101
proc recive_and_respond(bot: Bot) =
102
    let game_info: JsonNode = recievePacket(bot)
103
    echo(game_info)
104
    if game_info["Game"][0]["is_match_ended"].getBool() == true:
105
        raise newException(Exception, "Match Eneded")
106
    else:
107
        bot.send_inputs(game_info)
108
109
110
Mybot.try_connect(port = port)
111
var i: int = 0
112
while true:
113
    echo(i)
114
    Mybot.recive_and_respond()
115
    inc(i)