• New Horizons on Maelstrom
    Maelstrom New Horizons


    Visit our website www.piratehorizons.com to quickly find download links for the newest versions of our New Horizons mods Beyond New Horizons and Maelstrom New Horizons!

AI Sailing into the wind

Oh wait a second. Its not possible to have it as anything other than a boolean? Im trying to store values in it - bummer. Looks like ill have to devise a different way
 
Oh wait a second. Its not possible to have it as anything other than a boolean? Im trying to store values in it - bummer. Looks like ill have to devise a different way

Wait, aren't they inherently strings? You need to use 'float stf(ship.MyAttrib)' to use it as a float if I understand it correctly.

Try
Code:
ship.MyAttrib = 0.01;

but
Code:
float x = stf(ship.MyAttrib);
 
Well, whatever you are doing, it seems to be working. :drunk

No ctds so far, and in the one battle I got into all of the ships, 9 total, were turning this way and that with sails going up and down like they do in arcade mode. There was none of the old stuff where they all end up facing into the wind going backwards. :onya
 
This sounds absolutely great and by the sounds of it, you sure came further than I would've thought possible.
I LOVE being proven wrong! I think that warrants an inclusion in the Modders group. Welcome to the club, mate! :doff
(BTW: This will increase your forum attachment space to 10 MB)

I once messed around with the SailState code in PROGRAM\SEA_AI\sea.c for the furling of the sails when anchoring:
Code:
if (stf(tempMainChar.LastSailState) != 0.0) SendMessage(&AISea, "laf", AI_MESSAGE_SHIP_SET_SAIL_STATE, tempMainChar, 0.0);
I never got crashes from that but then I don't think anyone would ever run it within five seconds of loading the scene.

Am I correct in assuming you already managed ships to "remember" their attributes yet?
Let me know if there's any other issues you have and I'll see if I can figure out anything to help you.
 
Funny thing:
My train of thought was as follows - If Y is a vertical axis(as shown by the tacking code), then rotating either around X, or Z axis should allow me to implement ship heeling in the wind. So I checked it. Turns out:
- Z-axis doesn't exist, or rotating around it doesn't change a thing
- rotating around X-axis by 0.5 makes the ship sail sideways.... :shrug Let me reiterate - it does not rotate the ship. It rotates the speed vector of the ship.

And thus, it turns out that it's possible to implement leeway :onya
 
This sounds absolutely great and by the sounds of it, you sure came further than I would've thought possible.
I LOVE being proven wrong! I think that warrants an inclusion in the Modders group. Welcome to the club, mate! :doff
(BTW: This will increase your forum attachment space to 10 MB)

I once messed around with the SailState code in PROGRAM\SEA_AI\sea.c for the furling of the sails when anchoring:
Code:
if (stf(tempMainChar.LastSailState) != 0.0) SendMessage(&AISea, "laf", AI_MESSAGE_SHIP_SET_SAIL_STATE, tempMainChar, 0.0);
I never got crashes from that but then I don't think anyone would ever run it within five seconds of loading the scene.

Am I correct in assuming you already managed ships to "remember" their attributes yet?
Let me know if there's any other issues you have and I'll see if I can figure out anything to help you.
Arrr! happy to come aboard captain :cheers

Thanks! It took a lot longer than i thought it would, but fortunately the method works, and quite convincingly. Thanks for the increase to 10mb, im running into that atm! I managed to get ships to 'remember' attributes through using them as a flag/boolean - ie on or off. Ill try using them as a float per Flayed One's suggestions because that would allow a counter (far more useful). The ships tack quite well at the moment and I dont want to make their paths too wide by keeping them on one or the other side of the wind for a long time, but keeping them out of the wind for a bit longer than currently occurs would really improve their performance.

Even now though, good luck catching a Xebec, sloop or cutter in a square rigger while tacking upwind

Funny thing:
My train of thought was as follows - If Y is a vertical axis(as shown by the tacking code), then rotating either around X, or Z axis should allow me to implement ship heeling in the wind. So I checked it. Turns out:
- Z-axis doesn't exist, or rotating around it doesn't change a thing
- rotating around X-axis by 0.5 makes the ship sail sideways.... :shrug Let me reiterate - it does not rotate the ship. It rotates the speed vector of the ship.

And thus, it turns out that it's possible to implement leeway :onya

If it helps at all, arCharShip.Speed.z seems to be the actual speed of the ship in knots.


Ive attached a new version with a 50% increase to how quickly ships cross the wind; I noticed they were turning a bit slowly compared to how quickly the player can cross the wind. To anyone using it, please report back with any thoughts you have on how the AI performs in tacking, positive or negative, and especially any issues you run into and any ways you think it could be improved - im particularly interested to hear people's thoughts on what the best strategy on tacking upwind is in their experience and what it should be for the AI - eg straight line short width zig zag or long and wide zig zag that minimizes crossing of the wind. Is it better to cross the wind directly or to turn backwards and make a long swooping 270 degree turn? Is it better to sail on one side of the wind for longer, displacing the wind compared to the target and thus allowing pursuing of the target with only one crossing of the wind, or to continue crossing the wind many times but thus leave the target upwind?

These are all open questions really and ive never really had a chance to compare these methods and find what is the fastest method of tacking upwind. Right now the AI is significantly slower tacking regardless, but the aim is to make them as effective as the player (notwithstanding that the AI seems to sail about 10-20% slower than the player, even with 10 sail and leadership - another issue that i might post about later, but so far my experience has been that if AI does 8kn with a ship of mine, if i take over I might reach 9-9.5kn) - in order to do that i need to know what the aim is and what method is best
 

Attachments

  • AIShip.c
    195.3 KB · Views: 108
I don't know what the real world practice is. My tacking strategy is that the wind changes every hour at the hour or 4 minutes after, and it usually changes to head on. That means that just before the hour I change course to 90 degrees to the course I want in the hope of "fooling" the wind into helping me instead of hindering me. So, I tack every hour unless there is something in the way forcing an early tack.
 
I don't know what the real world practice is. My tacking strategy is that the wind changes every hour at the hour or 4 minutes after, and it usually changes to head on. That means that just before the hour I change course to 90 degrees to the course I want in the hope of "fooling" the wind into helping me instead of hindering me. So, I tack every hour unless there is something in the way forcing an early tack.

That there is what we would call 'superstition' xD:
As far as i know the wind changes to a limited degree from what it was previously, and following an overall 'trend'. I dont think player ship's facing is an issue!

Even if it did, im not sure paranoid AI turning into the wind every hour is a good idea!
 
Testing the latest file, it seems I must have a very slow turning ship. The ai ships could do a 360 before I could do a 90. It was especially noticeable after I captured a surrendered class 2 Spanish War Galleon. We both had to do a 180 to go to our next target, and that monster made its turn and was sailing away long before I finished my turn. :sail

It seems to me the ai tack too much when sailing into the wind. I tack less than they do and can pull away from them even though I'm sailing the slowest ship. Also, in combat they like to position themselves directly downwind from their opponent, making them combat ineffective. It would be nice if they slid off to one side a bit.


Superstitious? Whatever..... It usually takes me 3-9 hours to get in or out of port because of the constant headwinds combined with no room to tack.
 
Superstitious? Whatever..... It usually takes me 3-9 hours to get in or out of port because of the constant headwinds combined with no room to tack.

Thats true, sometimes it really does feel like the engine is out to get us!

Testing the latest file, it seems I must have a very slow turning ship. The ai ships could do a 360 before I could do a 90. It was especially noticeable after I captured a surrendered class 2 Spanish War Galleon. We both had to do a 180 to go to our next target, and that monster made its turn and was sailing away long before I finished my turn. :sail

It seems to me the ai tack too much when sailing into the wind. I tack less than they do and can pull away from them even though I'm sailing the slowest ship. Also, in combat they like to position themselves directly downwind from their opponent, making them combat ineffective. It would be nice if they slid off to one side a bit.

What ship were you using and did you have your sails down? Crossing the wind is much faster with sails at 50% and some momentum than at 0%.

The method I am using uses the same value for all AI ships, regardless of type, but it only helps the AI turn while they are facing the wind within about a 90 degree arc. After that, they turn according to their own turning values. Because, as you noticed, the AI turn too often and cross the wind too much (something im trying to solve by using character attributes) they suffer compared to the player, so the values I use see them turn their ship across the wind slightly faster than a player would - but certainly not so fast that they could do a 360 where a player manages a 90 degree turn. It should be close to what a player manages and again, only while facing the wind.

The issue with their not sliding to one side in combat is chance, and was always a problem in stock and why they sailed backwards. They dont necessarily like to do it, but they dont do anything about it either. With them now tacking, there is some possibility that they will slide off to one side, but because they tack very often at the moment in a narrow path, that possibility is low.

Both these things will hopefully be resolved somewhat when i change the method to use character attributes, allowing me to keep them out of the wind for longer, and I will investigate how to make their turning rate dependent on their turn rating. For the moment they are not very good tackers so that a player in the same ship is quite a bit better (unfortunately this is the case for almost all situations in the game and combat), but at least they are good enough that they can escape a player in a square rigger with sloops, xebecs or cutters.
 
You should be able to use character attributes that are values rather than just bools. :yes
 
Ok Ive finally figured out how to set character attributes. Turns out I was doing too much, not too little. Take this example:
Code:
float BS = arCharShip.bla;
float BS2 = BS + 2;
float BS3 = BS2 + 3;
archarship.bla = BS3;
Log_SetStringToLog("bla " + arCharShip.bla + " BS " + BS + " BS2 " + BS2 + " BS3 " + BS3);

This works, and what it does is set float BS to character attribute 'bla', then float BS2 to BS + 2, then BS3 to equal BS2 + 2, and finally writes the value to character attribute 'bla' again. Then it reports everything in the log.

The trouble with what i was doing before was that I was using
Code:
CheckAttribute(arCharShip,"bla")
to read the attribute. I now realise this is not correct - this command only checks whether the character attribute exists or not and returns 1 or 0 to indicate this.

The next mistake I was doing was trying to use 'stf' and other commands to set and read the character attribute. None of that is necessary. I was making this mistake because the code i used to learn and base how to do this only used character attributes as a 1/0 'flag' not a storage for values, and I tried to use the same method to store values.

I realise this is routine stuff for you guys but i was scratching my head over this for quite a while.

With this figured out I should be able to get the ships to tack better
 
[/quote]

What ship were you using and did you have your sails down? Crossing the wind is much faster with sails at 50% and some momentum than at 0%.
[/quote]



I was talking about the class 4 merchant fluyt. Since it usually only goes 2-3 knots anyway leaving any sails up means it will quickly be sailing backwards. Besides, at that speed there is no difference in turning with sails up or down since you don't even have steerage speed.
 
Well, i am just debugging and tweaking my latest method for AI tacking, this one is a lot more sophisticated and has ships staying to one side of the wind for a specified time, then crossing.

The trick is - how long do you keep them out of the wind, and what values do you use because if you do it right the AI can be given the option of 'forcing' a crossing of the wind if it wants to badly enough, but be kept out of the wind the rest of the time. In any case, I have a few savegames I always use to test the tacking and im much happier with this method than the simple one ive released. I would estimate at least a doubling or tripling of tacking performance by the AI. Once I release it though, what will remain to be seen is the drawbacks - forcing AI to stay one side of the wind or messing with their sails can have consequences on the risk of collisions, and ill be interested to see whether people's experience will be more collisions and whether that would be acceptable.

In terms of the quick crossing of the wind by the AI, I toned that down by 33%. Ultimately, I would like to read a ship's maximum turn rate and use that instead, but at the moment its a 'one size fits all' value for all ships.
 
Well 'debugging and tweaking' turned into 'general performance comparisons' and it turns out that improving on my current method (once i had begun forcing AI sails to 100% near the wind) was quite tricky. Still, I now have a few methods and improvements.

Would people like it if the quality/method of tacking used depended on the ship's sailing skill? Im almost done doing this, starting with ships at sail skill 1 being very poor and making little headway into the wind (often faltering in the wind), getting much better by skill 3, 4 and 5 and making long cuts across the wind by 6-10.

Right now i am concerned about a couple of issues -
1) Whether the AI will keep up with the player even with these changes. Its getting quite hard to make improvements.
2) Whether the risk of collisions is acceptable. There is almost certainly a higher risk, especially as i now force AI to go to 100% sails in quite a wide band
Code:
closest point + (RS_CP_OFFSET * 8)
, around 60-300 degrees if it has its sails up. They still stop and all when they reach the player but theres a possibility that in confined places like ports or with cliffs around they may hit the wall where they would otherwise stop - particularly if i force the AI to sail alongside the wind for a couple of minutes or more. I wonder whether the increased risk of collisions will be worth the improved tacking performance - that will fall to users to evaluate I guess.
 
Tacking ability determined by the Captain's skills? Ship performance based on the Captain's skills is already modeled in general. Does that also apply to tacking? I would not want that to be applied twice. Testing required.


Collisions? The AI have always been crashing into cliffs. The current model has them getting out of ports well. I'm wondering about short runs in tight spots vs long runs between tacks on the open sea. More testing!
 
Tacking ability determined by the Captain's skills? Ship performance based on the Captain's skills is already modeled in general. Does that also apply to tacking? I would not want that to be applied twice. Testing required.


Collisions? The AI have always been crashing into cliffs. The current model has them getting out of ports well. I'm wondering about short runs in tight spots vs long runs between tacks on the open sea. More testing!

The differences in performance based on captain's skill dont strike me as very large or prominent. Ship performance based on captain's skill would otherwise apply to tacking only with boosts to speed (if any) which would be minor. For most other purposes a ship with sailing skill 1 would tack just as well as one with 10. With the method i am working on, there is a very large and appreciable difference between very poor sailing skills of 1-3, and smaller but significant differences thereafter. I should point out, however, that the current simple method that i have released (ie the one you have seen) is used at sailing skill 3, and even at sail skill 2 I use a method that is better than the method i released where AI did not reduce sails. So tacking is generally improved across the board.


Collisions are the big question. The current method works well to get ships out of port because of the short strokes and the fact i do not force sails UP on tacking ships. However, the methods i am working on use long strokes and force sails up and i wonder if this will mean more collisions.


Ill get it finished so you can try it for yourself
 
Would it be possible for the ships to "know" which side the land is on and then decide not to tack in the direction of land if it's there?
You should be able to get some land/shore locator coordinates somehow and calculate a distance, though I'm not at all sure how.
 
Would it be possible for the ships to "know" which side the land is on and then decide not to tack in the direction of land if it's there?
You should be able to get some land/shore locator coordinates somehow and calculate a distance, though I'm not at all sure how.

That would be ideal, as would 'knowing' when a ship is putting down sails because of a collision and not forcing its sails up.

Ie, normally, when a ship comes to a cliff/other ship it puts down its sails and starts to turn away. If i could detect that AI flag or something, i could stop forcing its sails up and avoid a collision.

If i could supplement that with, as you say, avoiding a tack toward land, then it would work even better.


Aside from the fact i dont qutie know HOW to do this, there are other tradeoffs with these kinds of manipulations of AI routines. If the AI is tacking into port, for example, will it still be effectively able to do that? What if the player purposely comes close to land in the hope the AI will tack away from land out to sea? The thing is, by switching sides at regular intervals you effectively build in a 'cliff awareness' anyway, because once the AI encounters a cliff on the one side it will cross the wind again and move in the other direction for the set interval, then cross again - but the set interval will no longer bring it within reach of the cliff. So its somewhat redundant to do it when deciding which side to tack to. It all requires testing. I think to start, detecting when the AI is 'avoiding' a collision would be best
 
I'm now sailing the Dolphin Xebec (xebecAS)instead of a fluyt in order to see how a more maneuverable ship compares to the AI. I'm still getting out turned. First it was an English bark, then a light frigate, but the killer was when an English Galleon with its two main masts down evaded my attempts to board it. It ended up getting sunk.

They seem to generally be avoiding cliffs better now. In one battle early on when I was in a class 5 pinnace with a caravel escort we got into it with a light frigate in a cove with the wind coming in the throat. Several times we were up against the cliff with sails furled turning. Once the caravel came barreling in at full sail and rammed the frigate. :shock That is rare but I have seen it before. Fred Bob once sunk a frigate with a fluyt doing that many months ago. :onya

At Guadaloupe they had trouble getting out of port one time out of three so far. They ended up just going around in circles and I had to go to the world map to get them out. They will sometimes spin in other ports as well.
 
Back
Top