Experimental Code: Stop mobs hopping when pathing - FindBestZ tweaks
This is for those people who don't like to see mobs hopping vertically when pathing.
I've spent the past few days tweaking the 'FindBestZ' code so that mobs stay on the ground when moving. It seems to work quite well, so I thought I would put it out there for anyone interested to try it out. (For those that don't know, the FindBestZ code attempts to use the geometry data in the zone .map file to ensure mobs stay on the ground while moving). Diffs against the 1062 source, along with the three changed source files (Map.cpp, waypoints.cpp and features.h) can be found here: www.rama.demon.co.uk/BestZPatch.zip No Windows binaries as I use Linux for playing with EQEmu. The changes in features.h are just to enable the defines related to fixing pathing when moving, along with a new define I added, ASSIGN_BESTZ_WAYPOINTS_ON_LOAD, which, if defined, causes BestZ to be applied to waypoints as they are loaded from the database. Notes: What I did find while testing was that the Facelist array in the eastwastes map appears to be corrupt. This was causing a crash, so I added a check for this in FindBestZ, in the same way that is currently done in the LOS code. Of course, this means that FindBestZ won't work for Eastern Wastes. There may be other map files that are 'corrupt' in a similar manner, although I didn't come across any others in my limited testing. I guess this code will break pathing in underwater zones, e.g. Kedge, where mobs are actually not meant to move along the floor. I guess you could add a column to the zone table to enable/disable this code on a per zone basis. This could also be helpful to reduce CPU load for zones where the pathing correction isn't required, e.g. zones that are mostly flat or zones where the waypoints have been made by hand to avoid hopping. |
Just in case anyone was curious what the MAP files actually contain, during my work on this I wrote a little Visual C++ 8.0 / OpenGL app so I could visualise it (3D geometry is not really my thing).
The image below shows the triangles contained in the dreadlands.map file, looking from the tunnel to Firiona Vie out across the zone (the box in the middle is Karnor Castle). The text shows the X,Y,Z position you are viewing from, along with the Node (bounding box). The next line shows some info about the bounding box and finally the BestZ, i.e. the elevation of the ground at the X,Y position you are at. The app is not user friendly (need to hard code the path to the zone file as well as the X,Y,Z position you want to look from, otherwise I would have posted the code for that too. http://www.rama.demon.co.uk/Dreadlan...ualisation.jpg |
Nice work!!
|
Very nice, does this also fix mobs going under the world while attempting to path over hills? If so, you are my hero! If not, still very nice :).
|
Aye, this is fascinating work! The problem's obviously less easy to solve than I originally thought.
Thanks again for the eye opener. |
Quote:
If you can give me some specific examples of where this occurs, I can check those out for you. |
Awesome!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!!
I've wanted to see some solid work on this for quite a while. Excellent job. Now we need some Windows binaries :D |
Quote:
|
Do you have any idea where the crash in question occurs in the code?
Corrupt or not there's probably safe-checks that can be put in place to prevent it if we know where it's at. |
Http://www.rogean.com/Zone-BestZ.exe
Haven't tested it myself. Test it out and let me know how it works out. If it looks good I'll commit to code. |
Quote:
No crashes occur because I copied the check from: bool Map::LineIntersectsNode( NodeRef node_r, VERTEX p1, VERTEX p2, VERTEX *result, FACE **on) which is called by the LOS checking code Code:
unsigned long *cfl = mFaceLists + _node->faces.offset; I put the same check in the FindBestZ code to avoid the crash there, so there is nothing else required (other than maybe fixing the program that generates the .map files (azone?). |
if this does work and stops the mobs from hopping all we need now is the actuallt pathing in "apath" figured out. I have been looking at it for awhile now and I am not making any heads or tails on it and I gave up about a mnth ago figuring it was hopeless.
|
Yeah it would be azone that generates them, alright I'll look at it when I take a look at the other stuff posted on the forums in the next couple days.
|
Nice. I have comitted a cleaned up version of this code.... hopefully it still works. I disabled the two old options by default in features.h, but enabled the new "fix-at-load-time" feature, as it seems like a good compromise.
My only real concern about this is the somewhat arbitrary nature of a lot of the constants in there... 10, 20, 45, etc... We might want to either make them a rule, so people can easily change them, or else put some serious thought into deciding on good universal values... My last thought is that if this in fact turns out to be a rock solid fix for the z hopping problem, then we should prolly take it one step further. One of the things I was trying to accomplish with apathing was to be able to load, fix, and then re-save the pathing data into the database... this way we only consume the CPU time once... it shouldent be all that hard to accomplish, the big concern is how to be sure that it is actually producing the right data... we dont want to run it against the official dbs unless we are quite sure it isnt going to mangle a bunch of paths... one challenge with stuff like this is trying to figure out how to detect such failues... as in most cases the mobs are then just way under the ground, and nobody will ever notice (unless its a named mob).... just a thought. -FNW |
I'm excited about this but man... I've already designed a large part of my DB with grids that won't make npc's go through hills. So much work! At least this will make the rest of my work much easier.
|
I've downloaded the latest Win32 release: EQEmu-0.7.0-1065
==11/29/2007 FatherNitwit: (Derision) Fix BestZ pathing cleanup code top stop hopping. FatherNitwit: (Derision) New fix-z-on-load feature. and tested a few zones that always drove me mad with the hopping: fieldofbone frontiermtns The mobs are still hopping like mad in these zones. I'll test out some other zones soon. |
Quote:
the Zone.exe that Rogean posted a little earlier in this thread, or I will attempt to build a Win32 release with all 3 options enabled in the next few days. |
Quote:
I will give that a try. A proper Win32 release with all the options enabled would be greatly appreciated. |
OK, by popular demand (aka one dude who cant build), I reworked this stuff to be runtime configurable using the rules system.
|
Quote:
Hopping is gone. What a sweet fix! |
Pathing Fix
I have created a wiki page listing the new rules required for the pathing Z fix.
Krusher |
to make the rules work(or to even compile properly).. need to add them to the rulesys..
Code:
--- ruletypes.h 2007/11/14 06:13:36 1.11 Code:
--- waypoints.cpp 2007/11/30 19:06:27 1.6 |
Quote:
Quote:
Tested with 0.7.0-1068 and it works a treat. |
Thanks guys, really excited about this new feature.
|
Working great, only problem i've noticed is when a mob goes up a steep hill or maybe it's just a certain change in his z coordinate, he goes under the world. However he does pop back up after a couple seconds. Still a huge improvement.
I may have not set it up right though, not exactly sure what the 'rule system' is. |
Quote:
Here is how I have mine set up (working very well): rule_sets http://img216.imageshack.us/img216/6...setsnz6.th.jpg rule_values http://img229.imageshack.us/img229/3...lueskj5.th.jpg Thats all there is to it! |
Sweet thanks, got it working, still seeing them go under when climbing steep hills. Not sure if that's fixable. I haven't upgraded to the newest build though, didn't see any fixes in the log. Btw do you know what the Map:FixPathingZatWaypoints is for?
|
Quote:
I've seen this happen in Dreadlands where one waypoint is on one side of a large mountain and the next waypoint is on the other side. The movement code plots a vector between the two waypoints which goes right through the middle of the mountain (under the world). The BestZ code as currently implemented takes the mobs current Z position and looks downward to find the ground. If the mob is already under the world, it will either do nothing, or in the worst case, e.g. Dreadlands, which for some reason has an invisible 'floor' under the world at Z=-210, it will push the mob even further down. I just made a quick hack to the code to make the BestZ code look up instead of down, and in the case of the particular mob I was looking at in Dreadlands which pathed over a steep hill, it seemed to have the desired effect of stopping it going under the world, i.e. if it was under the world, it pushed it back up to the ground level. The next step is to have the code look up AND down and decide which direction to push the mob. I don't have a lot of time to play with this much at the moment, but if I find something which seems to work reliably, I'll post a further patch. |
Quote:
|
Quote:
So what if you forced the z coord of the waypoint a mob is headed to always be the highest point in the zone. Then they wouldn't go through hills and the z-fix already in place would keep them on the ground. Would that work? |
Quote:
The code does already try and compensate for a small movement under the ground. If it can't find a BestZ on the first attempt, it bumps the mob up by 10 Z units and tries again. The amount it tries to move the mob up on the second attempt (10 units) is not currently configurable by the rules system. I'll see if tuning this number (increasing it) helps with the steep hill problem. This would be a less CPU intensive solution then my previous thought, and if it works, we could make this a configurable parameter in the rules system. |
This is a great Improvement over what we had -
It always seemed to me there were much more "hoppers" when the grids were packet spawned, than when I laid them out my self. On thing still remains, is the water hoppers - a good example is in Dagnor's Cauldron, where there are many surface swimmers, all will bounce up and down constantly. If you go to the small isle in the middle, you can follow the roamers into the water and watch them hop |
Quote:
A more complete solution would be to add an extra table to the database. Each row would contain the zone number and the co-ordinates of a 3D cube defining underwater areas (with multiple rows for zones with multiple distinct areas of water). This should allow the BestZ code to quickly check if the mob is underwater and not force it to the bottom or top of the water. I will experiment with this if I have some free time over the holidays. |
Cavedude had mentioned one temporary solution was to give the swimmers the levitation spell - This keeps them steady at what ever grid they are on. Problem is these mobs in Cauldron go in and out of water, so they float on land, and it doesn't look right.
What I'm thinking is. what code is related to levitate? maybe make an "in water" exception and apply what ever it is that removes the "gravity" in Levitate, while swimming. There must be some code that tells the NPC he is in water and this puts him in "swim-mode" (they start swimming while in water). Maybe you can exploit this and use it to eliminate the hopping too (while in swim mode, don't use Z coord). |
Quote:
Maybe I'll try making a zone with Windcatcher's OpenZone with some areas of water and see if the client detects when a player is underwater. If it does, then there must be some information in the S3D that I can extract and use. |
ive also noticed that mobs that stand on docks or in little huts are pulled through and stuck to the actual ground so they either under water or there head is sticking through the floor...
im possibly gona try and add a way to disable fixZ for selected NPCs as for water hopping... could check if NPC is in water or not(if possible).. and if its in water walk in a straight line.. (maybe, just an idea) |
I think an ignorefixz column or something such would be a good addition to npc_types. I too, have found that mobs get glued to the ground when they should be on rocks, huts, chairs, etc. This column would allow us to place exceptions on a per mob basis. The initial setup would be nuts of course, but once most of those mobs are corrected everything will look a lot better. Better yet, the column could be put in spawn2, so any mob that has those spawn points will be effected.
As for mobs in the water... there currently is no way for us to tell where water exists in the map. That's why you can fish anywhere in a zone, and why we can't keep fish from leaving ponds and such. However, if a way of determining where water is can be found, that would enable us to correct fishing, prevent fish and the like from leaving water, and help prevent the hopping under water and/or sticking to the bottom if fixedz is enabled. |
heres what i came up with today...
Code:
--- mob.h 2007/12/17 02:26:10 1.25 Code:
--- npc.cpp 2007/12/17 02:26:10 1.20 Code:
--- npc.h 2007/12/17 02:26:10 1.15 Code:
--- spawn2.cpp 2006/11/01 20:36:21 1.3 Code:
--- spawn2.h 2006/06/20 02:36:21 1.2 Code:
--- waypoints.cpp 2007/12/01 18:11:14 1.7 let me know :) EDIT:: forgot.. you have to add column in spawn2 table... fixZ tinyint[4] 0 no null default 1 |
Sweet! I'll try this out on my test box when I get home.
|
Mental note to install EQ at work for "testing".
|
All times are GMT -4. The time now is 04:45 PM. |
Powered by vBulletin®, Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.