ID:2103649
 
(See the best response by Lummox JR.)
Code:
proc/Walk_Towards(var/mob/ref,var/atom/trg,var/lag=0,var/speed=16)
set waitfor=0
if(trg==0){ref.Target=0;ref.L.Remove(ref.L)}
else if(ref.Target==0)
ref.Target=trg
FixTarget(get_turf(ref),get_turf(ref.Target),ref)

var/atom/start=get_turf(ref); var/turf/end=get_turf(ref.Target);

while(trg<>null&&ref.Target<>0 && start<>end)

if(ref.L.len==0){ref.L=AStarSearch(start,end,ref)}

var/diagpenalty=1;
if(get_dir(ref,ref.L[1])==NORTHEAST || get_dir(ref,ref.L[1])==NORTHWEST|| get_dir(ref,ref.L[1])==SOUTHEAST|| get_dir(ref,ref.L[1])==SOUTHWEST){diagpenalty=sqrt(2)}
ref.glide_size=(16)*world.tick_lag/lag

if(get_dist(ref,ref.L[1])>1){step_towards(ref,ref.L[1],16)}else{step(ref,get_dir(ref,ref.L[1]),16)}
if(ref.loc==ref.L[1]){ref.L.Remove(ref.L[1])}

sleep(lag*diagpenalty)
start=get_turf(ref);end=get_turf(ref.Target)
ref.Target=0
else //this just changes the target
ref.Target=trg
ref.L.Remove(ref.L)
FixTarget(get_turf(ref),get_turf(ref.Target),ref)


Problem description:
I have a problem with my Walk_Toward proc, for a reason it works normally at first but after some time average real-time increases really fast until the whole game crashes.(walking proc is used with a formation of mobs so there are nearly 40 mobs moving together)

so here is the code. also I've noticed that when I am near average realtime increases but when I go far it decreases...
also FixTarget() is used to change the target in the event that the target is dense so it changes the target to the nearest available. I use no density in the map so it never does anything in this test.
Best response
The indentation on that is super messed-up, so it's hard to tell what the logic is supposed to look like. With the indentation broken, it's possible that this isn't sleeping when you mean it to. I also don't see any logic for undoing an existing walk, so multiple versions of this proc might run concurrently for the same mob.

Indents aside, a few things that aren't right in this code:

- if(trg==0) is likely to never be true, because if anything you'll pass a null and not a number. That should be if(!trg) instead. Same with the ref.Target check. Never use ==0 when checking for falsehood; use the ! operator.

- Calling get_dir() repeatedly is no bueno. Call it once and store it in a var.

- You don't need to compare the direction to each of the four diagonals. All you need is if(thedir & (thedir-1)), which will check to see if it has more than one bit set.

- get_dist() doesn't distinguish between targets on the same z level, or different; it will give you the max of the x, y, or z distance. You should test for different-z cases if you use get_dist().

Also on a more general note, having a mob var named "T" isn't likely to be very helpful. Use short names like that for local vars and arguments in procs, and descriptive ones for your mob vars.
Yeah I dont use walk instancess its a simple proc.
There is only 1 proc for each mob, checked that so the logic is:
if(trg==0)makes target 0 thus the walk loop will stop.
the 2nd if is the real walk to target
and the 3rd is the change of target
ok I will use !
yeah I would change that as well about get_dir
hmm yeah you're right about get_dist, so far I've only tested on 1 level, so that saved me time from debugging later, I'll just use my heuristic getDist() which distinguishes it.

But I have this weird thing going on here when I move my mob away so the moving mob is out of the screen the problem stops and the realtime decreases... I use a tile size of 16 btw and I have 40 mobs (16x16 each) move simultaneously. I achieve that by having 1 formation manager mob which does all the pathing and then it updates the paths for the 40 mobs. But its not the pathfinding that lags so worry not about that its the walk proc itself.

edit: by instances I mean I haven't created a class that handles movement I decided to keep it all in a proc

just checked with 100 mobs the same thing happens I have a slight increase with pathfinding but it is really small to cause lag, its this proc it start low and gradually the lag increases... what do you think might be causing this? I checked sleep and the amount is correct... maybe something bad happens with Cross() and other procs like step_to or step_towards
hmmm ok I found the culprit I created a proc to display the tiles per realtime seconds and I noticed that when I use glide the speed gradually falls from 0.33 tiles/second to 0.1
but when I have glide disabled it is near 0.33 for the whole movement
Thanks for the help anyways that get_dist() stuff has potentially saved me a lot of time of debugging :)

I just noted that I used 100fps and combined with glide step of 1 it must have put a lot of strain on the cpu.
Btw which is the optimal fps for a game?? some guidelines I mean
I know that it is used instead of directly setting tick_lag so I guess having fps of 100 allows 10 ticks per second. while lower fps allows less ticks per second. So that equals less verbs etc?? So far I had no problems except movement with 100 fps. What do you guys suggest??
why would you use 100 fps...
"Optimal" FPS is kind of a fuzzy concept. What you want to do always for performance is to keep FPS as low as you can, but high enough that it looks good. (One of the items on my list to look at for 511 is to see if I can get the client to tick at a higher rate, and apply gliding to pixel step movement.)

High FPS currently will put more strain on both the server and the client. The latter is usually not a big deal unless you're spamming the screen with effects or have lots of multi-tile screen objects. The former gets to be a problem if you have a lot of players, since more players means more work for the server.

20 and 25 FPS should have a really nice smoothness improvement over the default 10, and they both have the advantage of dividing evenly into 1000 ms. (Actual tick_lag is an integer number of milliseconds, so good FPS choices to divide evenly are 10, 20, 25, 40, and 50.) While 100 divides nicely, 10 ms isn't a lot of time for the client to do its work, and that would be easy to overstress.
In response to Lummox JR
When you say stuff like 20 and 25 fps, makes me so angry.
nah Im good about server this is a singleplayer and multiplayer up to 6 players so its all cool. And to be honest all the heavy stuff is off the multiplayer.
So yeah I guess I'm gonna expirament with it and see whats the optimal fps, everything works perfectly besides gliding at 100 fps though.
Also I really don't think there is much use for pixel movement when you can have glide movement or a smaller grid. I mean 16x16 works just fine in most games in my opinion. Totaly out of topic but while I was trying to create a pathfinder for pixel movement (complete failure though since I found no resources for navmeshes) I came up with the idea of grouping up turfs for use in pathfinding. In my own pathfinder I group non-dense turfs to areas and break the pathfinding into smaller targets and use the appropriate accuracy for near and far targets. So could we treat a 1x1 pixel as a node and make certain groups and work the same way?? Far targets will be easy to calculate since instead of using 1x1 nodes there will be a group of them meaning less calculations but when doind the near very acurate stuff it could put some limitations. But I believe its doable I mean I can just change my grid representation from 16x16 to 1x1 and it will theoretically work. any thoughts on that??
No particular thoughts on it; pathfinding with pixel movement is a tricky business for sure. Grouping areas together is generally a good strategy.
gonna try it out for fun I believe I can get it to work but it will most likely be useless in a real game