• Welcome to Valhalla Legends Archive.
 

D2GS Locations 0x03 (C>S)

Started by lokis, February 12, 2008, 08:56 PM

Previous topic - Next topic

lokis

Hello, I've been reading this foruns for a couple weeks now, and I started to code a "bot" in fact I just make a program that connects to Bnet and log into a game.
But now I want my char to move, and I cannot understand the 0x03 packet, I mean:

03 65 15 61 12
(WORD) X location
(WORD) Y location

How this X location and Y location are calculated?

For example, the town map in act one has:
57 cells - Width
41 cells - Height

This mean, in coordinates:
285 subcells - X
205 subcells - Y

How can i convert this X, Y based on the subcells, to the X, Y I have to send in the packet?
I need this because I draw like a minimap on the screen, and I want the char to go the location I click.
Anyone knows how to do that?

Thanks

Barabajagal

Packet log the actual game, and look at that packet. See where your character is when it's sent, and calculate how it's determined. Either that or read the Assembly.

Ringo

#2
Quote from: lokis on February 12, 2008, 08:56 PM
Hello, I've been reading this foruns for a couple weeks now, and I started to code a "bot" in fact I just make a program that connects to Bnet and log into a game.
But now I want my char to move, and I cannot understand the 0x03 packet, I mean:

03 65 15 61 12
(WORD) X location
(WORD) Y location

How this X location and Y location are calculated?

For example, the town map in act one has:
57 cells - Width
41 cells - Height

This mean, in coordinates:
285 subcells - X
205 subcells - Y

How can i convert this X, Y based on the subcells, to the X, Y I have to send in the packet?
I need this because I draw like a minimap on the screen, and I want the char to go the location I click.
Anyone knows how to do that?

Thanks

Im not exacly sure what your asking, but if you want to get the game poition of a tile (cell) then you just multiply the X/Y from packet S>C 0x07 by 5, and that will give the true X/Y location. Most area tiles are 40 by 40, some 60 by 60 (and few are uniquely sized)
Also note, that up(+y) is bottom left of your d2 screen, and right(+x) is bottom right.

Asuming your character is in the middle of the screen/mini map, you can get the distance from the X/Y of the click Vs screen middle X/Y, then add the differnce (multiplyed by what ever scale your drawing at) to your characters X/Y, and send that in packet C>S 0x03

lokis

Yeah, but I'm trying to understand how the client make this packets

I logged the packets send by my char while I was walking around town

0000  03 46 12 C9 11                   
0000  03 42 12 C8 11                               
0000  03 3F 12 C4 11                                 
0000  03 3E 12 BC 11                                 
0000  03 3B 12 B8 11                                 
0000  03 38 12 B5 11                                 
0000  03 34 12 B4 11                                 
0000  03 32 12 B2 11                                 
0000  03 2D 12 B1 11                                 
0000  03 29 12 B3 11                                 
0000  03 28 12 B8 11

So, in the first packet my location X would be 46 12, and Y = C9 11
But these are high numbers, so the way I'm thinking isn't right

Why the second byte in locations always repeat?
I walked around all the map and the bytes 12 and 11 didn't change

The location are calculated this way right?
(0,0) ------------------------> X
|
|
|
\/   Y

Because is like that the map is read from the .ds1 file, if not, I'm being really dumb!   :-X

Ringo

#4
Quote from: lokis on February 12, 2008, 09:32 PM
Yeah, but I'm trying to understand how the client make this packets

I logged the packets send by my char while I was walking around town

0000  03 46 12 C9 11                   
0000  03 42 12 C8 11                               
0000  03 3F 12 C4 11                                 
0000  03 3E 12 BC 11                                 
0000  03 3B 12 B8 11                                 
0000  03 38 12 B5 11                                 
0000  03 34 12 B4 11                                 
0000  03 32 12 B2 11                                 
0000  03 2D 12 B1 11                                 
0000  03 29 12 B3 11                                 
0000  03 28 12 B8 11

So, in the first packet my location X would be 46 12, and Y = C9 11
But these are high numbers, so the way I'm thinking isn't right

Why the second byte in locations always repeat?
I walked around all the map and the bytes 12 and 11 didn't change
Well, those (WORD)'s are integers, so 46 12 would be 0x1246 and C9 11 is 0x11C9
This image below shows the cells and walkable terran with in them:
(Cells are the blue squares, character X/Y walkable terrans are white/black)

This image is offseted, so it would fit on the screen.
You just need to remember, no matter where you stand on the map, your characters X/Y is the middle of the graphic screen, so from that, you can work out where to draw everything useing the distance from your char X/Y then drawing stuff at that distance (multiplyed by scaleing) to your mini map.
The cell X/Y from S>C 0x07 just needs to be multiplyed by 5 to line up with the character X/Y

Quote from: lokis on February 12, 2008, 09:32 PM
The location are calculated this way right?
(0,0) ------------------------> X
|
|
|
\/   Y
ye  :)
DIablo 2 client just rotates the axes by 95° before drawing.

EDIT:
Heres are old screen shot of a simple GUI i made for one of my chat bots ages ago:

You can see that my necro (next to teleportal) is always drawn to the middle, then everything else is drawn based on distance from his X/Y.
Also just a side note, in that screen shot, Y is flipped, as in vb6.0, Y direction is oppersite to C++/C# i think.
But it gives you a good idea of what im talking about

lokis

Thanks, I understand now.

I was thinking the locations were relative to the map. Like, if my char was standing on map townE1.ds1 in location (150,50) of the map, the X and Y location would be that. I was thinking like in other games where the maps aren't together like Diablo.


You wrote the code to draw that minimap?
I wrote one, but my map isn't quite right yet, I don't know what is walkable and what is not, I just read the walls layer and put them as unwalkable. but this isn't right because I'm seting a whole cell as unwalkable, and a wall cell can have walkable subcells.
Do you know how to calculate exactly what is walkable and what is not?
If you knew what the 4 bytes in each cell mean, it would hep me a lot.




Ringo

Quote from: lokis on February 12, 2008, 10:14 PM
Do you know how to calculate exactly what is walkable and what is not?
If you knew what the 4 bytes in each cell mean, it would hep me a lot.
D2 would load up .ds1 files for each cell, it does this by generating the map with S>C 0x03 seeds, to know what ds1 to load for a cell.
Persionaly i have never opened a ds1 in my life, but there are other ways to detect what cell is what, but they are very hard to do. The most common way would be to hard code offsets of things in the game, but thats a very messy way of doing it.
Im not to sure what 4 bytes your talking about tho :P

lokis

hehehe, ok, i thought your minimap was draw based on .ds1 files
I prefere building the minimap using the map files. But I need some documentation about it, if I get anything I'll share here.

lokis

Is there any way to know what map my char is when I logon?
I mean, imagine if I'm in act1, there are 3 possible maps, how is determinated which map you're supposed to draw? Is this send by any packet?

Ringo

#9
Yeah, the maps are generated with the seeds in S>C 0x03, but emulating that is pretty big task.
Also there is 4 versions of a1 town (N/E/S/W), 2 versions of a2 (exit West/North), 1 version of a3/4/5.
You could always use somthing like the stash location/cell offset to determin what version it is.
Somthing like:
Bool =  (cell.x * 5) => StashX and (cell.x * 5) + 40 =< StashX and cell.y * 5 => StashY and (cell.y * 5) + 40 =< StashY
then if bool then use that cells offset as referance to determin the town version or somthing.

lokis

hmmm, ok
but I guess the others random maps I can't generate right? they are all generated by this seed?
like cold plains in act1..

Ringo

yeah, any map that is randomized is defined by those seeds.
Its just very hard to emulate the map generating function.
There is other ways to build the map, but they are not very easy, it depends manly on the area you are trying to generate, the object placement, and how many pre/post areas you have seen before it.
I persionaly build them on the fly, by making bots detect patterns from large prelogs of other games, but even that has a chance to encounter new varyations and somtimes build the map slightly wrong.
Most areas are fairly easy to generate based on doing that, others (like alot of act1 maps) are very very hard.

lokis

thanks for the tip
:D
i'll work in a solution