更新攻打航舰,加油任务效果

This commit is contained in:
2026-02-09 02:30:44 +08:00
parent fbb0fe1767
commit 2e3d0fe492
20 changed files with 1797 additions and 15 deletions

364
processors/addfuelstate.txt Normal file
View File

@@ -0,0 +1,364 @@
# File generated by Wizard 2.9.0 on Feb 8, 2026.
# File generated by Wizard 2.9.0 on Feb 3, 2026.
# File generated by Wizard 2.9.0 on Dec 26, 2024.
processor sta WSF_SCRIPT_PROCESSOR
update_interval 10 s
script_variables
double orbitLength = 20000000;
string state = "";
//
string PointOrName1 = "XL04";
string zoneType1 = "polygon";
double Radius = 50000;
bool iscrea = false;
bool isaddfuel = false;
WsfGeoPoint p1 = WsfGeoPoint.Construct("16:16:24.77n 146:53:27.50e");
end_script_variables
script bool RecvTask()
bool rev = false;
string sojna = PLATFORM->plat1Name;
if(sojna.Contains("j"))
{
rev = true;
}
return rev;
end_script
//
//@ flyZone to a point
//
script void flyZone(string PointOrName,string zoneType)
if(zoneType == "circle")
{
WsfGeoPoint p = p.Construct(PointOrName);
PLATFORM.GoToSpeed(1000,999,true);
PLATFORM.GoToLocation(p);
}
else if(zoneType == "polygon")
{
WsfZone zone = zone.FindZone(PointOrName);
PLATFORM.GoToSpeed(1000,999,true);
PLATFORM.GoToLocation(zone.Location());
}
end_script
//
//@ bool
script bool isInZone(string PointOrName,string zoneType)
if(zoneType == "circle")
{
WsfGeoPoint p = p.Construct(PointOrName);
return(PLATFORM.Location().GroundRangeTo(p) <= 10);
}
else if(zoneType == "polygon")
{
WsfZone zone = zone.FindZone(PointOrName);
return(PLATFORM.Location().GroundRangeTo(zone.Location()) <= 10000);
}
return false;
end_script
//
// @ generateCirclePoints
//
script Array<WsfGeoPoint> generateCirclePoints(string Center , double radius)
WsfGeoPoint center = WsfGeoPoint.Construct(Center);
Array<WsfGeoPoint> circlePoints = {};
double earthRadius = 6371000.0;
double angularDistance = radius / earthRadius;
Array<double> angles = {10,20,30,40,50,60,70,80,90,100,110,120,130,140,150,160,170,180,190,200,210,220,230,240,250,260,270,280,290,300,310,320,330,340,350,360};
foreach(double angle in angles)
{
double latCenter = center.Latitude() * MATH.PI() / 180.0;
double lonCenter = center.Longitude() * MATH.PI() / 180.0;
double lat = MATH.ASin(MATH.Sin(latCenter)
* MATH.Cos(angularDistance)
+ MATH.Cos(latCenter)
* MATH.Sin(angularDistance)
* MATH.Cos(angle));
double lon = lonCenter + MATH.ATan2(MATH.Sin(angle)
* MATH.Sin(angularDistance)
* MATH.Cos(latCenter)
,MATH.Cos(angularDistance)
- MATH.Sin(latCenter)
* MATH.Sin(lat));
circlePoints.PushBack(WsfGeoPoint.Construct(lat*180.0/MATH.PI(),lon * 180.0 / MATH.PI(),5000));
}
return circlePoints;
end_script
//
//@ circle execute
//
script void executecircularPatrol()
Array<WsfGeoPoint> circlePoints = generateCirclePoints(PointOrName1,Radius);
WsfRoute route;
WsfRoute r1 = route.Create("lx");
foreach(WsfGeoPoint vertex in circlePoints)
{
vertex.SetAltitudeHAE(10000);
r1.Append(vertex,1500);
}
r1.Waypoint(0).SetLabel("start");
r1.Waypoint(r1.Size() - 1).SetGoToLabel("start");
PLATFORM.FollowRoute(r1);
r1.Print();
end_script
//
// @ bounds execute
//
script void executeBoundsAreaPatrol()
WsfZone zone = zone.FindZone(PointOrName1);
Array<WsfGeoPoint> boundsPoints = zone.PolyPoints();
WsfRoute route;
WsfRoute r1 = route.Create("lx");
foreach(WsfGeoPoint vertex in boundsPoints)
{
vertex.SetAltitudeHAE(10000);
r1.Append(vertex,1500);
}
r1.Waypoint(0).SetLabel("start");
r1.Waypoint(r1.Size() - 1).SetGoToLabel("start");
PLATFORM.FollowRoute(r1);
end_script
//
//execute once patrol
//
script void executeOncePatrol()
if(zoneType1 == "circle")
{
executecircularPatrol();
}
else if( zoneType1 == "polygon")
{
executeBoundsAreaPatrol();
}
end_script
//
//
script void TurnOnJam()
WsfProcessor pro = (WsfProcessor)PLATFORM.Processor("jamming");
if(pro.IsTurnedOff())
{
pro.TurnOn();
}
end_script
//
script void TurnOffJam()
WsfProcessor proc = (WsfProcessor)PLATFORM.Processor("jamming");
if(proc.IsTurnedOn())
{
proc.TurnOff();
}
end_script
script bool isontime()
return true;
end_script
////////////////////////////////////////////////////////////////////
script_variables
string tankerName = "yy20_1";
bool isrecvMessage = false;
string proName = "task_mgr";
end_script_variables
script bool isRefuelRequired()
WsfFuel fuel = PLATFORM.Fuel();
if(fuel.IsValid())
{
double i = fuel.MaximumQuantity();
double j = i * 0.45;
if(fuel.QuantityRemaining() <= j)
{
return true;
}
}
return false;
end_script
script void sendRefuelMessage(string tankname)
if(WsfSimulation.FindPlatform(tankname).IsValid())
{
WsfComm trackComm = WsfSimulation.FindPlatform(tankname).Comm("sub_net");
WsfMessage warningMessage = WsfMessage();
warningMessage.SetType("FUELING");
warningMessage.SetSubType(PLATFORM.Name());
PLATFORM.Comm("sub_net").SendMessage(warningMessage,trackComm);
}
else
{
writeln(PLATFORM.Name()," is inVaild");
}
end_script
on_message
type CANFUEL
script
WsfMessage warningMessage = (WsfMessage)MESSAGE;
isrecvMessage = true;
end_script
type default
script
writeln(PLATFORM.Name()," Report: Message received");
end_script
end_on_message
script bool isRecvMessage()
return isrecvMessage;
end_script
script void gotoTanker()
WsfPlatform p = WsfSimulation.FindPlatform(tankerName);
if(p.IsValid())
{
PLATFORM.GoToSpeed(p.Speed() * 1.5,999);
PLATFORM.GoToLocation(p.Location());
}
end_script
script bool isShift()
WsfPlatform p = WsfSimulation.FindPlatform(tankerName);
if(p.IsValid())
{
if(PLATFORM.GroundRangeTo(p) <= 10000)
{
return true;
}
}
return false;
end_script
script void shift()
WsfPlatform p = WsfSimulation.FindPlatform(tankerName);
if(p.IsValid())
{
PLATFORM.GoToSpeed(p.Speed() * 1.1,999);
PLATFORM.GoToLocation(p.Location());
}
end_script
script bool isRefuelOk()
WsfFuel fuel = PLATFORM.Fuel();
if(fuel.IsValid())
{
if(fuel.QuantityRemaining() >= fuel.MaximumQuantity() - 300)
{
isrecvMessage = false;
isaddfuel = true;
return true;
}
return false;
}
return true;
end_script
//////////////////////////////////////////////////////////////////////////////////
execute at_time 1 s relative
SetState("STARTJA");
end_execute
state STARTJA
next_state DETECTEDJA
return isontime();
end_next_state
end_state
state DETECTEDJA
on_entry
flyZone(PointOrName1,zoneType1);
end_on_entry
next_state AREAPATROLJA
return (isInZone(PointOrName1,zoneType1));
end_next_state
//
end_state
state AREAPATROLJA
on_entry
executeOncePatrol();
end_on_entry
next_state SENDMESSAGE
return isRefuelRequired();
end_next_state
end_state
state Jamming
on_entry
TurnOnJam();
end_on_entry
next_state SENDMESSAGE
return isRefuelRequired();
end_next_state
on_exit
TurnOffJam();
end_on_exit
end_state
state SENDMESSAGE
on_entry
sendRefuelMessage(tankerName);
end_on_entry
next_state GOTOTANKER
return isRecvMessage() && !isaddfuel;
end_next_state
on_exit
end_on_exit
end_state
state GOTOTANKER
on_entry
end_on_entry
next_state SHIFTFLY
gotoTanker();
return isShift();
end_next_state
on_exit
end_on_exit
end_state
state SHIFTFLY
on_entry
end_on_entry
next_state STARTJA
shift();
return isRefuelOk();
end_next_state
on_exit
PLATFORM.GoToLocation(p1);
PROCESSOR.TurnOff();
end_on_exit
end_state
end_processor

272
processors/patrol_fuel.txt Normal file
View File

@@ -0,0 +1,272 @@
# File generated by Wizard 2.9.0 on Feb 3, 2026.
processor bs_fueling WSF_SCRIPT_PROCESSOR
update_interval 10 s
script_variables
double fuelRate = 50.0;
Array<string> mplatforms = Array<string> ();
bool isFuel = false;
double addFuelRange = 30000;
WsfGeoPoint p1 = WsfGeoPoint.Construct("32:04:34.53n 130:51:05.36e");
string CenterPoint = "23:49:20.14n 121:01:08.01e";
double Radius = 50000;
bool isOver = false;
string zoneName = "JY01";
string shape = "polygon"; //polygon circle
bool aendflag = false;
end_script_variables
//
// @ generateCirclePoints
//
script Array<WsfGeoPoint> generateCirclePoints(string Center , double radius)
WsfGeoPoint center = WsfGeoPoint.Construct(Center);
Array<WsfGeoPoint> circlePoints = {};
double earthRadius = 6371000.0;
double angularDistance = radius / earthRadius;
Array<double> angles = {10,20,30,40,50,60,70,80,90,100,110,120,130,140,150,160,170,180,190,200,210,220,230,240,250,260,270,280,290,300,310,320,330,340,350,360};
foreach(double angle in angles)
{
double latCenter = center.Latitude() * MATH.PI() / 180.0;
double lonCenter = center.Longitude() * MATH.PI() / 180.0;
double lat = MATH.ASin(MATH.Sin(latCenter)
* MATH.Cos(angularDistance)
+ MATH.Cos(latCenter)
* MATH.Sin(angularDistance)
* MATH.Cos(angle));
double lon = lonCenter + MATH.ATan2(MATH.Sin(angle)
* MATH.Sin(angularDistance)
* MATH.Cos(latCenter)
,MATH.Cos(angularDistance)
- MATH.Sin(latCenter)
* MATH.Sin(lat));
circlePoints.PushBack(WsfGeoPoint.Construct(lat*180.0/MATH.PI(),lon * 180.0 / MATH.PI(),5000));
}
return circlePoints;
end_script
//
//@ circle execute
//
script void executecircularPatrol()
Array<WsfGeoPoint> circlePoints = generateCirclePoints(CenterPoint,Radius);
WsfRoute route;
WsfRoute r1 = route.Create("lx");
foreach(WsfGeoPoint vertex in circlePoints)
{
vertex.SetAltitudeHAE(10000);
r1.Append(vertex,1500);
}
r1.Waypoint(0).SetLabel("start");
r1.Waypoint(r1.Size() - 1).SetGoToLabel("start");
PLATFORM.FollowRoute(r1);
r1.Print();
isOver = true;
end_script
//
// @ bounds execute
//
script void executeBoundsAreaPatrol()
WsfZone zone = WsfZone.FindZone(zoneName);
Array<WsfGeoPoint> boundsPoints = zone.PolyPoints();
WsfRoute route;
WsfRoute r1 = route.Create("lx");
foreach(WsfGeoPoint vertex in boundsPoints)
{
vertex.SetAltitudeHAE(10000);
r1.Append(vertex,1500);
}
r1.Waypoint(0).SetLabel("start");
r1.Waypoint(r1.Size() - 1).SetGoToLabel("start");
PLATFORM.FollowRoute(r1);
isOver = true;
end_script
/////////////////////////////////////////////////////////////
script bool isAlreadyInQueue(string name)
for(int i = 0; i < mplatforms.Size(); i = i + 1)
{
if(mplatforms.Get(i) == name)
{
return true;
}
}
return false;
end_script
script int sendMessage()
if(!mplatforms.Size() == 0)
{
if(WsfSimulation.FindPlatform(mplatforms.Front()).IsValid())
{
WsfPlatform p = WsfSimulation.FindPlatform(mplatforms.Front());
# if(p.FuelRemaining() < p.FuelBingoQuantity())
# {
WsfComm trackComm = WsfSimulation.FindPlatform(mplatforms.Front()).Comm("sub_net");
WsfMessage warningMessage = WsfMessage();
warningMessage.SetType("CANFUEL");
warningMessage.SetSubType(PLATFORM.Name());
PLATFORM.Comm("sub_net").SendMessage(warningMessage,trackComm);
return 0;
# }
}
else
{
return 0;
}
}
return 0;
end_script
script bool isRange()
if(mplatforms.Size() != 0)
{
WsfPlatform p = WsfSimulation.FindPlatform(mplatforms.Front());
if(p.IsValid())
{
if(PLATFORM.GroundRangeTo(p) <= addFuelRange)
{
return true;
}
}
else
{
mplatforms.Reverse();
mplatforms.PopBack();
mplatforms.Reverse();
return false;
}
}
return false;
end_script
script bool gotoFuel(double fuelRange,double fuelRate)
WsfPlatform p = WsfSimulation.FindPlatform(mplatforms.Front());
if(p.IsValid())
{
WsfFuel reciveFuel = p.Fuel();
WsfPlatform tank = PLATFORM;
WsfFuel tankFuel = tank.Fuel();
if(!tankFuel.IsValid())
{
writeln("This Platform : ",p.Name()," no fuel!!!!");
return true;
}
if(PLATFORM.SlantRangeTo(p) < fuelRange)
{
reciveFuel.SetQuantityRemaining(reciveFuel.QuantityRemaining() + (fuelRate * 1));
tankFuel.SetQuantityRemaining(tankFuel.QuantityRemaining() - (fuelRate * 1));
writeln("zhengziagei ; ",p.Name());
}
if(reciveFuel.QuantityRemaining() >= reciveFuel.MaximumQuantity()-300)
{
isFuel = true;
}
}
else
{
isFuel = true;
}
return isFuel;
end_script
//
////////////////////////////on_message///////////////////////////////
//
on_message
type FUELING
script
WsfMessage warningMessage = (WsfMessage)MESSAGE;
string originator = warningMessage.Originator();
if(!isAlreadyInQueue(originator))
{
mplatforms.Insert(mplatforms.Size(), originator);
}
writeln(PLATFORM.Name()," Report: FUELING from ", originator);
end_script
type default
script
writeln(PLATFORM.Name(),"Report: Message received");
end_script
end_on_message
script bool isArrayNull()
return mplatforms.Size() > 0;
end_script
script void updateArray()
if(mplatforms.Size() != 0)
{
mplatforms.Reverse();
mplatforms.PopBack();
mplatforms.Reverse();
isFuel = false;
}
end_script
///////////////////////////////////////////////////////////////////
execute at_time 1 s absolute
PROCESSOR.SetState("start");
end_execute
///////////////////////////////////////////////////////////////////
state start
next_state DETECTED
return true;
end_next_state
end_state
state DETECTED
on_entry
if(!aendflag)
{
executeBoundsAreaPatrol();
}
end_on_entry
next_state gotoTarget
return isArrayNull();
end_next_state
on_exit
end_on_exit
end_state
state gotoTarget
on_entry
writeln("--------------------- :",mplatforms.ToString());
# sendMessage();
end_on_entry
next_state FUEL
sendMessage();
return isRange();
end_next_state
on_exit
end_on_exit
end_state
state FUEL
on_entry
end_on_entry
next_state DETECTED
return gotoFuel(addFuelRange,fuelRate);
end_next_state
on_exit
updateArray();
PLATFORM.GoToLocation(p1);
aendflag = true;
end_on_exit
end_state
end_processor

View File

@@ -3,13 +3,13 @@ zone tw
polygonal lat_lon
maximum_altitude 20 km
point 25:39:39.36n 120:30:25.18e
point 25:06:17.31n 122:29:29.13e
point 21:32:49.50n 121:05:56.86e
point 22:19:43.20n 119:36:49.51e
point 30:03:45.52n 126:02:30.89e
point 30:53:53.49n 126:31:12.66e
point 30:29:11.10n 127:04:22.94e
point 29:36:19.04n 126:22:36.55e
fill_color red
line_color red
fill_color blue
line_color blue
end_zone
processor randomPatrol WSF_SCRIPT_PROCESSOR

164
processors/ucavFire.txt Normal file
View File

@@ -0,0 +1,164 @@
processor ucavFire WSF_TASK_PROCESSOR
track_update_interval 5.0 sec
script_variables
string SENSOR_NAME;
string WEAPON_NAME;
int SALVO_SIZE = 2;
string mTrackTaskStr = "Track";
string mShootTaskStr = "Shoot";
end_script_variables
script bool FiringNow()
return (WeaponsActiveFor(TRACK.TrackId()) > 0);
end_script
script bool InInterceptEnvelopeOf(WsfPlatform shooter)
if (shooter.IsNull() || !shooter.IsValid()) return false;
WsfWeapon w = shooter.Weapon(WEAPON_NAME);
if (!w.IsValid()) return false;
if (w.LaunchComputer().IsValid())
return w.CanIntercept(TRACK);
return (shooter.GroundRangeTo(TRACK) <= 150000.0);
end_script
script bool InInterceptEnvelopeOfAnySub()
foreach (WsfPlatform sub in PLATFORM.Subordinates())
{
if (InInterceptEnvelopeOf(sub)) return true;
}
return false;
end_script
script bool TrackingNow()
return (TasksAssignedFor(TRACK.TrackId(), mTrackTaskStr) > 0);
end_script
script void ReleaseResources()
CancelTask(TRACK.TrackId());
end_script
script bool LaunchWeapon()
WsfWeapon weapon;
WsfPlatform platform;
foreach (WsfPlatform sub in PLATFORM.Subordinates())
{
weapon = sub.Weapon(WEAPON_NAME);
if (weapon.IsTurnedOn() &&
(weapon.QuantityRemaining() >= SALVO_SIZE) &&
(TasksAssignedTo(sub, "", weapon.Name()) < 1) &&
InInterceptEnvelopeOf(sub))
{
platform = sub;
break;
}
}
bool launched = false;
if (weapon.IsValid() && !platform.IsNull())
launched = Fire(TRACK, mShootTaskStr, weapon.Name(), SALVO_SIZE, platform);
return launched;
end_script
script bool IsAssignable()
return ((PLATFORM == PLATFORM.Commander()) ||
(TasksReceivedFor(TRACK.TrackId()) > 0) ||
(OperatingLevelFor("ENGAGE") > 0));
end_script
script int WeaponsAvailable(WsfPlatform aAssignee)
WsfWeapon weapon = aAssignee.Weapon(WEAPON_NAME);
if (!weapon.IsTurnedOn()) return 0;
return weapon.QuantityRemaining();
end_script
script int TotalWeaponsAvailable()
int quantity = 0;
foreach (WsfPlatform sub in PLATFORM.Subordinates())
quantity = quantity + WeaponsAvailable(sub);
return quantity;
end_script
script bool Engage()
if (TotalWeaponsAvailable() < 1)
{
writeln("Engage: no weapons available");
return false;
}
foreach (WsfPlatform sub in PLATFORM.Subordinates())
{
if (TasksAssignedTo(sub, TRACK.TrackId(), mTrackTaskStr) > 0) continue;
WsfSensor sensor = sub.Sensor(SENSOR_NAME);
if (!sensor.IsValid())
{
writeln("Engage: sub ", sub.Name(), " sensor ", SENSOR_NAME, " invalid");
continue;
}
int maxTrack = sensor.MaximumRequestCount("TRACK");
if (maxTrack > 0 && sensor.ActiveRequestCount("TRACK") >= maxTrack)
{
writeln("Engage: sub ", sub.Name(), " TRACK slots full");
continue;
}
if (TRACK.BelievedAlive() && InInterceptEnvelopeOf(sub))
{
bool ok = StartTracking(TRACK, mTrackTaskStr, sensor.Name(), "default", sub);
writeln("Engage: StartTracking ", sub.Name(), " -> ", ok);
if (ok) return true;
}
}
writeln("Engage: no sub assigned for ", TRACK.TargetName());
return false;
end_script
evaluation_interval DETECTED 2.0 sec
state DETECTED
next_state DETECTED
if (TRACK.IFF_Friend()) { CancelTask(TRACK.TrackId()); return true; }
return false;
end_next_state
next_state ENGAGEABLE
return (TRACK.BelievedAlive() && !TRACK.IFF_Friend() && IsAssignable());
end_next_state
end_state
evaluation_interval ENGAGEABLE 2.0 sec
state ENGAGEABLE
next_state DETECTED
if (TRACK.BelievedDead() || TRACK.IFF_Friend() ||
((TasksAssignedFor(TRACK.TrackId(), "ENGAGE") < 1) && !IsAssignable()))
{ ReleaseResources(); return true; }
return false;
end_next_state
next_state ENGAGE
bool didEngage = Engage();
bool trackNow = TrackingNow();
int assigned = TasksAssignedFor(TRACK.TrackId(), mTrackTaskStr);
writeln("ENGAGEABLE->ENGAGE: didEngage=", didEngage, " trackNow=", trackNow, " assigned=", assigned, " target=", TRACK.TargetName());
return (trackNow && (assigned > 0));
end_next_state
end_state
evaluation_interval ENGAGE 2.0 sec
state ENGAGE
next_state ENGAGEABLE
if (TRACK.BelievedDead() || !TrackingNow() || !IsAssignable())
{ ReleaseResources(); return true; }
return false;
end_next_state
next_state FIRING
if (TRACK.BelievedAlive() && TrackingNow() && !FiringNow() && InInterceptEnvelopeOfAnySub())
return LaunchWeapon();
return false;
end_next_state
end_state
evaluation_interval FIRING 2.0 sec
state FIRING
next_state ENGAGE
return (TRACK.BelievedDead() || !InInterceptEnvelopeOfAnySub() ||
(!FiringNow() && (TasksAssignedFor(TRACK.TrackId(), mShootTaskStr) < 1)) ||
(TotalWeaponsAvailable() < 1) || !TrackingNow());
end_next_state
end_state
end_processor