Scripters cove
Moderators: winston, another_commander
- Diziet Sma
- ---- E L I T E ----
- Posts: 6312
- Joined: Mon Apr 06, 2009 12:20 pm
- Location: Aboard the Pitviper S.E. "Blackwidow"
Re: Scripters cove
Thanks! I'll see what I can cobble together.
Most games have some sort of paddling-pool-and-water-wings beginning to ease you in: Oolite takes the rather more Darwinian approach of heaving you straight into the ocean, often with a brick or two in your pockets for luck. ~ Disembodied
- phkb
- Impressively Grand Sub-Admiral
- Posts: 4830
- Joined: Tue Jan 21, 2014 10:37 pm
- Location: Writing more OXPs, because the world needs more OXPs.
Re: Scripters cove
Is there a way using JS to tell if a new game has just been started?
- Wildeblood
- ---- E L I T E ----
- Posts: 2453
- Joined: Sat Jun 11, 2011 6:07 am
- Location: Western Australia
- Contact:
Re: Scripters cove
Context - why would you care?phkb wrote:Is there a way using JS to tell if a new game has just been started?
- phkb
- Impressively Grand Sub-Admiral
- Posts: 4830
- Joined: Tue Jan 21, 2014 10:37 pm
- Location: Writing more OXPs, because the world needs more OXPs.
Re: Scripters cove
I'd like to send an email to the player telling about their purchase of their ship.
Re: Scripters cove
Not strictly, no - the routine to load a saved game and the routine to start a new scenario differ only in which directory they get thephkb wrote:Is there a way using JS to tell if a new game has just been started?
oolite-save
file from.You can probably make a fair guess by looking at the clock, but I don't guarantee to take care to preserve that to the second between Oolite versions. (To the day, probably - if the day is 2084004, and you haven't already delivered that email, you can safely do so)
- Smivs
- Retired Assassin
- Posts: 8408
- Joined: Tue Feb 09, 2010 11:31 am
- Location: Lost in space
- Contact:
Re: Scripters cove
Then you can spam them with market research surveys, customer satisfaction questionaires and offers linked to the purchase. And they'll probably need reminding to leave Feedback!phkb wrote:I'd like to send an email to the player telling about their purchase of their ship.
Commander Smivs, the friendliest Gourd this side of Riedquat.
- Wildeblood
- ---- E L I T E ----
- Posts: 2453
- Joined: Sat Jun 11, 2011 6:07 am
- Location: Western Australia
- Contact:
Re: Scripters cove
Clock won't be reliable if scenarios catch on with OXPers. Folk won't always start with a new Jameson to create their oolite-save files. More likely the'll use an old one and just delete the mission variables; it wouldn't occur to me to reset the clock, and if it did why should all scenarios start at the same time?
Re: Scripters cove
I'm trying to get my head around these new docking toys. I managed to create a highly restricted station that allows the player to dock only if specifically allowed. And player actually crashes, if he/she tries to dock without permission. However, getting disallowedDockingCollides to work was a bit of a pain as I first need to set allowsDocking to false. To my understanding that affects possible NPCs too. I'm wondering what happens, if the station launches a defense ship that tries to dock later if allowsDocking is set to false.
Is there a way to set a station to disallowedDockingCollides so that all ships without docking permission would collide? A shipdata property disallowed_docking_collides would be nice .
Is there a way to set a station to disallowedDockingCollides so that all ships without docking permission would collide? A shipdata property disallowed_docking_collides would be nice .
Re: Scripters cove
Given that scenarios may not even allow the email OXP to load in the first place, and even if they do might have their own ideas for what initial emails the player should get - "Congratulations on your recent theft of this Boa Freighter" - that's probably more a feature than a bug if the OXP has to have specific checks for each separate scenario.Wildeblood wrote:Clock won't be reliable if scenarios catch on with OXPers. Folk won't always start with a new Jameson to create their oolite-save files. More likely the'll use an old one and just delete the mission variables; it wouldn't occur to me to reset the clock, and if it did why should all scenarios start at the same time?
Re: Scripters cove
spara wrote:Is there a way to set a station to disallowedDockingCollides so that all ships without docking permission would collide? A shipdata property disallowed_docking_collides would be nice .
allowsDocking
false is really intended for situations like "this is a launch-only dock with some sort of high-speed launch catapult, and you're not getting your ship back in there" or "you could dock here, but not while the bay doors are closed"I could set it up so that per-ship rejection on the dock through a method parallel to
acceptDockingRequestFrom
would have disallowedDockingCollides
apply in that case, but that would need re-testing every frame. (That's probably acceptable as the method shouldn't be particularly intensive)Re: Scripters cove
A game mechanic change of crashing the player when docking without permission instead of fining would be an interesting one .cim wrote:spara wrote:Is there a way to set a station to disallowedDockingCollides so that all ships without docking permission would collide? A shipdata property disallowed_docking_collides would be nice .allowsDocking
false is really intended for situations like "this is a launch-only dock with some sort of high-speed launch catapult, and you're not getting your ship back in there" or "you could dock here, but not while the bay doors are closed"
I could set it up so that per-ship rejection on the dock through a method parallel toacceptDockingRequestFrom
would havedisallowedDockingCollides
apply in that case, but that would need re-testing every frame. (That's probably acceptable as the method shouldn't be particularly intensive)
Anyway, I solved my little problem of conditionally offering higher TL services with a simple mission screen override so I'm happy with the current status quo.
- phkb
- Impressively Grand Sub-Admiral
- Posts: 4830
- Joined: Tue Jan 21, 2014 10:37 pm
- Location: Writing more OXPs, because the world needs more OXPs.
Re: Scripters cove
I'm still working on my little rename ship tweak (talked about here), but I'm going into bits of Oolite I have no experience with whatsoever.
In case your wondering, I'm trying to add some purpose to the process of renaming your ship, and giving the player the opportunity to use this strategically. Rename the ship (with a small cost), and potentially confuse any assassins waiting for you at the end of the witchspace tunnel. cim suggested a method of just overwriting the players roles, which I am testing as well, but (I think I'm correct in saying) this method would only work if the player is not carrying any parcels. If the assassins are after the player with a parcel, this wouldn't do anything.
So, my blunt force method, is to attach a JS script to any assassins in view when the player exits the wormhole. The script file has the following code in it:
Essentially, if the ship's target is the player, and our confusion process is in operation, and the player hasn't done anything silly like attack the ship (which would set the "this._disable" to true, then we get into the nuts and bolts of the confusion. The "chanceOfSuccess" is 1 the first time the player renames the ship - this results in a 100% chance that the assassin will become confused. We then set the ship's target to null to clear their target. They just became confused. The ship might then send a message out, saying to keep looking for the original ship name.
Now, this code works. Player is targeted, ship is confused, and they un-target the player, message goes out, all is well.
Except I get this error:Which is not in my code at all, but in the default libraries. From what I can understand, because I've set the ship's target to null in the "shipTargetAcquired", there's a flowon impact in the core code.
So, I'm guessing that the "shipTargetAcquired" is the wrong place to set the ship's target to null. Is there a better place to do this? Should I do something a little more adventurous (and scary) with the AI stuff? I'm a little lost here!
In case your wondering, I'm trying to add some purpose to the process of renaming your ship, and giving the player the opportunity to use this strategically. Rename the ship (with a small cost), and potentially confuse any assassins waiting for you at the end of the witchspace tunnel. cim suggested a method of just overwriting the players roles, which I am testing as well, but (I think I'm correct in saying) this method would only work if the player is not carrying any parcels. If the assassins are after the player with a parcel, this wouldn't do anything.
So, my blunt force method, is to attach a JS script to any assassins in view when the player exits the wormhole. The script file has the following code in it:
Code: Select all
// if the ship targets the player, potentially untarget them
this.shipTargetAcquired = function(target) {
if (this._debug) log(this.name, "target acquired");
var w = worldScripts.RenameShipTweak;
if (target == player.ship && w._confusionActive == true && this._disable == false) {
if (this._debug) log(this.name, "player ship targetted");
if (Math.random() < (1 / w._chanceOfSuccess)) {
this._retarget = true;
this.ship.target = null;
if (w._confusedMessageSent == false) {
log(this.name, "sending confused message");
this.ship.commsMessage(expandDescription("[confused-message]", {shipname:w._storedShipName}), player.ship);
w._confusedMessageSent = true;
}
}
}
}
Now, this code works. Player is targeted, ship is confused, and they un-target the player, message goes out, all is well.
Except I get this error:
Code: Select all
13:53:41.072 [script.javaScript.exception.unexpectedType]: ***** JavaScript exception (Oolite Assassin AI 1.80): TypeError: this.ship.target is null
13:53:41.072 [script.javaScript.exception.unexpectedType]: Resources/Scripts/oolite-priorityai.js, line 2767.
So, I'm guessing that the "shipTargetAcquired" is the wrong place to set the ship's target to null. Is there a better place to do this? Should I do something a little more adventurous (and scary) with the AI stuff? I'm a little lost here!
Re: Scripters cove
So what's happening here is that the AI routine will have something like this:
It doesn't expect anything to have updated this.ship.target in between selecting it and trying to use it, so it doesn't check if it's still defined.
The easiest way to do it is probably to override
by doing something like
(Note that overriding core AI methods like this is possible and even encouraged, but should be carefully documented on your OXP's page so that OXPs which require the core behaviour for an AI method can use appropriate methods - including if necessary declaring incompatibility at the manifest level - to coexist)
One of the other problems - even if the log error didn't occur - with using shipTargetAcquired and then breaking the lock, is that this will trigger an almost immediate reevaluation of the AI's priorities (as always happens when they lose primary target). Since probably nothing material has changed, they will then attempt again to target the player... If
Code: Select all
this.ship.target = nearbySuitableTarget;
// later...
if (this.ship.target.property == something) {
The easiest way to do it is probably to override
conditionScannerContainsCourier
in the ship AIs. Currently it's this:
Code: Select all
PriorityAIController.prototype.conditionScannerContainsCourier = function()
{
return (this.checkScannerWithPredicate(function(s) {
return (this.shipInRoleCategory(s,"oolite-courier")) || (s.isPlayer && this.shipHasRiskyContracts(s));
}));
}
Code: Select all
ship.AIScript.oolite_priorityai.conditionScannerContainsCourier = function() {
return (this.checkScannerWithPredicate(function(s) {
if (s.isPlayer) {
// do the "recently renamed" checks here, return false if is ignoring the player
// this also means that the assassins will go after another courier instead if one happens to be about
}
return (this.shipInRoleCategory(s,"oolite-courier")) || (s.isPlayer && this.shipHasRiskyContracts(s));
}));
}
One of the other problems - even if the log error didn't occur - with using shipTargetAcquired and then breaking the lock, is that this will trigger an almost immediate reevaluation of the AI's priorities (as always happens when they lose primary target). Since probably nothing material has changed, they will then attempt again to target the player... If
w._chanceOfSuccess
is even slightly greater than 1, this will mean that within seconds they realise their mistake.- phkb
- Impressively Grand Sub-Admiral
- Posts: 4830
- Joined: Tue Jan 21, 2014 10:37 pm
- Location: Writing more OXPs, because the world needs more OXPs.
Re: Scripters cove
Cim, I'm really sorry. I'm a programmer and I should be able to work this out, but I mustn't have enough caffeine in my system, or I've eaten too many dark side cookies, or something, because I can't work this out.
So, I need to override
I tried a number of combinations of
Then I had a lightbulb moment and thought, what if I've been setting the script the wrong way? Yes, there is a
So, I've run out of ideas and really need some pointers. I guess, to summarise, I need to know these things: (1) Do I use the
So, I need to override
conditionScannerContainsCourier
- I created a JS file with my code in it, put it in the Scripts folder, then for each assassin at the witchpoint I tried ship.setScript("assassin-confused.js");
. I get this error:Code: Select all
17:28:51.434 [script.javaScript.load.failed]: ***** Error loading JavaScript script ../AddOns/RenameShipTweak.oxp/Scripts/assassin-confused.js -- could not run script
17:28:51.561 [script.javaScript.exception.unexpectedType]: ***** JavaScript exception (RenameShipTweak 1.0.0): TypeError: ship.AIScript.oolite_priorityai is undefined
ship.AIScript.oolite_priorityai.conditionScannerContainsCourier = function()
trying to get it to work, including (but not limited to):
Code: Select all
this.ship.AIScript.oolite_priorityai.conditionScannerContainsCourier
this.AIScript.oolite_libpriorityai.conditionScannerContainsCourier (for this one, the error was "this.AIScript is undefined")
ship.AIScript.PriorityAIController.conditionScannerContainsCourier
ship.AIScript["oolite-libPriorityAI"].conditionScannerContainsCourier
ship.AIScript.oolite_priorityAI.conditionScannerContainsCourier
ship.AIScript["Oolite Assassin AI"].conditionScannerContainsCourier
setAI
method! So I moved my script file to the AIs folder, and tried again.Code: Select all
19:16:43.227 [script.javaScript.exception.unexpectedType]: ***** JavaScript exception (RenameShipTweak 1.0.0): TypeError: ship.AIScript.oolite_priorityai is undefined
setAI
or setScript
method on the assassin ships? (2) Does my script need anything other than my overridden function in it? For instance, do I need a this.aiStarted = function()
if I load it via setAI
? (3) Have I missed anything obvious? (Actually, I think that's a given - feel free to answer that one or not!).