diff --git a/ActionSequencer/Program.cs b/ActionSequencer/Program.cs
index 3def67d..2e0c140 100644
--- a/ActionSequencer/Program.cs
+++ b/ActionSequencer/Program.cs
@@ -66,7 +66,7 @@ namespace IngameScript
continue;
}
int step = Int32.Parse(Ini.Get(key, "step").ToString("0"));
- IBlockAction blockAction = buildBlockAction(block, key);
+ BlockAction blockAction = buildBlockAction(block, key);
if (blockAction == null)
{
Console.Print($"Failed to add '{block.CustomName}' to action '{actionName}'.");
@@ -121,22 +121,22 @@ namespace IngameScript
}
// Prerequisite: Ini.Parse has already been called for this block.
- private IBlockAction buildBlockAction(IMyTerminalBlock block, string key)
+ private BlockAction buildBlockAction(IMyTerminalBlock block, string key)
{
if (block is IMyDoor)
{
- BlockActionDoor.DoorAction action;
+ DoorAction action;
switch (Ini.Get(key, "action").ToString("open"))
{
case "open":
- action = BlockActionDoor.DoorAction.Open;
+ action = DoorAction.Open;
break;
case "close":
- action = BlockActionDoor.DoorAction.Close;
+ action = DoorAction.Close;
break;
default:
Console.Print($"Invalid door action for '{block.CustomName}'. Defaulting to open.");
- action = BlockActionDoor.DoorAction.Open;
+ action = DoorAction.Open;
break;
}
diff --git a/DockingController/DockingController.csproj b/DockingController/DockingController.csproj
new file mode 100644
index 0000000..4126f8c
--- /dev/null
+++ b/DockingController/DockingController.csproj
@@ -0,0 +1,28 @@
+
+
+ netframework48
+ IngameScript
+ 6
+ false
+ Release;Debug
+ x64
+
+
+
+ all
+ runtime; build; native; contentfiles; analyzers; buildtransitive
+
+
+ all
+ runtime; build; native; contentfiles; analyzers; buildtransitive
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/DockingController/DockingController.mdk.ini b/DockingController/DockingController.mdk.ini
new file mode 100644
index 0000000..5add8f4
--- /dev/null
+++ b/DockingController/DockingController.mdk.ini
@@ -0,0 +1,22 @@
+; This file is project specific and should be checked in to source control.
+
+[mdk]
+; This is a programmable block script project.
+; You should not change this.
+type=programmableblock
+
+; Toggle trace (on|off) (verbose output)
+trace=off
+
+; What type of minification to use (none|trim|stripcomments|lite|full)
+; none: No minification
+; trim: Removes unused types (NOT members).
+; stripcomments: trim + removes comments.
+; lite: stripcomments + removes leading/trailing whitespace.
+; full: lite + renames identifiers to shorter names.
+minify=none
+
+; A list of files and folder to ignore when creating the script.
+; This is a comma separated list of glob patterns.
+; See https://code.visualstudio.com/docs/editor/glob-patterns
+ignores=obj/**/*,MDK/**/*,**/*.debug.cs
diff --git a/DockingController/DockingController.mdk.local.ini b/DockingController/DockingController.mdk.local.ini
new file mode 100644
index 0000000..4b66820
--- /dev/null
+++ b/DockingController/DockingController.mdk.local.ini
@@ -0,0 +1,7 @@
+; This file is _local_ to your machine and should not be checked in to source control.
+
+[mdk]
+; Where to output the script to (auto|specific path)
+output=auto
+; Override the default binary path (auto|specific path)
+binarypath=auto
\ No newline at end of file
diff --git a/DockingController/Instructions.readme b/DockingController/Instructions.readme
new file mode 100644
index 0000000..ed30ab7
--- /dev/null
+++ b/DockingController/Instructions.readme
@@ -0,0 +1,5 @@
+R e a d m e
+-----------
+
+In this file you can include any instructions or other comments you want to have injected onto the
+top of your final script. You can safely delete this file if you do not want any such comments.
diff --git a/DockingController/Program.cs b/DockingController/Program.cs
new file mode 100644
index 0000000..c990a9c
--- /dev/null
+++ b/DockingController/Program.cs
@@ -0,0 +1,91 @@
+using Sandbox.ModAPI.Ingame;
+using System.Collections.Generic;
+using VRage.Game.ModAPI.Ingame.Utilities;
+
+namespace IngameScript
+{
+ public partial class Program : MyGridProgram, IConsoleProgram
+ {
+ public IConsole Console { get; private set; }
+ public MyIni Ini { get; } = new MyIni();
+
+ private IEnumerator _job = null;
+ private MyCommandLine _cli = new MyCommandLine();
+
+ private List dockingPorts = new List();
+ private List thrusters = new List();
+ private List gasTanks = new List();
+
+ private ActionGroup actionGroup;
+
+ public Program()
+ {
+ Console = new MainConsole(this, "Docking Controller");
+ actionGroup = new ActionGroup(Console, "docking");
+
+ // We store a list of the dockingPorts because we will only dock if one is ready to lock.
+ GridTerminalSystem.GetBlocksOfType(dockingPorts, blockFilter);
+
+ foreach (IMyShipConnector dockingPort in dockingPorts)
+ {
+ actionGroup.AddActionBlock("dock", 0, new BlockActionConnector(dockingPort, ConnectorAction.Connect));
+ actionGroup.AddActionBlock("undock", 1, new BlockActionConnector(dockingPort, ConnectorAction.Disconnect));
+ }
+
+ List thrusters = new List();
+ GridTerminalSystem.GetBlocksOfType(thrusters, blockFilter);
+ foreach (IMyThrust thruster in thrusters)
+ {
+ actionGroup.AddActionBlock("dock", 1, new BlockActionThruster(thruster, ThrusterAction.Disable));
+ actionGroup.AddActionBlock("undock", 0, new BlockActionThruster(thruster, ThrusterAction.Enable));
+ }
+
+ List gasTanks = new List();
+ GridTerminalSystem.GetBlocksOfType(gasTanks, blockFilter);
+ foreach (IMyGasTank gasTank in gasTanks)
+ {
+ actionGroup.AddActionBlock("dock", 1, new BlockActionGasTank(gasTank, GasTankAction.Stockpile));
+ actionGroup.AddActionBlock("undock", 0, new BlockActionGasTank(gasTank, GasTankAction.Dispense));
+ }
+ }
+
+ public void Main(string argument, UpdateType updateSource)
+ {
+ if (argument != "")
+ {
+ _cli.TryParse(argument);
+ if (_cli.ArgumentCount == 0)
+ {
+ Console.Print("Error: Must pass an argument, 'dock' or 'undock'.");
+ }
+ else if (_job != null)
+ {
+ Console.Print("Already performing a docking action.");
+ }
+ else
+ {
+ _job = actionGroup.RunAction(_cli.Argument(0).ToLower());
+ Runtime.UpdateFrequency = UpdateFrequency.Update10;
+ }
+ }
+
+ if (_job != null && !_job.MoveNext())
+ {
+ _job.Dispose();
+ _job = null;
+ Console.Print("Docking action complete.");
+ Runtime.UpdateFrequency = UpdateFrequency.None;
+ }
+ }
+
+ private bool blockFilter(IMyTerminalBlock block)
+ {
+ if (MyIni.HasSection(block.CustomData, "docking"))
+ {
+ Ini.TryParse(block.CustomData);
+ return Ini.Get("docking", "ignore").ToBoolean(false);
+ }
+ return true;
+ }
+ }
+}
diff --git a/DockingController/thumb.png b/DockingController/thumb.png
new file mode 100644
index 0000000..a8dc2ef
Binary files /dev/null and b/DockingController/thumb.png differ
diff --git a/Mixins/ActionGroups/ActionGroup.cs b/Mixins/ActionGroups/ActionGroup.cs
index aa9118b..d73a213 100644
--- a/Mixins/ActionGroups/ActionGroup.cs
+++ b/Mixins/ActionGroups/ActionGroup.cs
@@ -30,7 +30,7 @@ namespace IngameScript
}
// Add an action to the sequence called actionName, which will be created if it doesn't already exist.
- public void AddActionBlock(string actionName, int step, IBlockAction actionBlock)
+ public void AddActionBlock(string actionName, int step, BlockAction actionBlock)
{
if (!_actions.ContainsKey(actionName)) _actions[actionName] = new ActionSequence(actionName);
_actions[actionName].Add(step, actionBlock);
diff --git a/Mixins/ActionGroups/ActionGroups.projitems b/Mixins/ActionGroups/ActionGroups.projitems
index a265255..c9b57b6 100644
--- a/Mixins/ActionGroups/ActionGroups.projitems
+++ b/Mixins/ActionGroups/ActionGroups.projitems
@@ -8,9 +8,12 @@
+
+
-
+
+
\ No newline at end of file
diff --git a/Mixins/ActionGroups/ActionGroups.shproj b/Mixins/ActionGroups/ActionGroups.shproj
index 83aa175..e29dcb1 100644
--- a/Mixins/ActionGroups/ActionGroups.shproj
+++ b/Mixins/ActionGroups/ActionGroups.shproj
@@ -14,6 +14,6 @@
bin\Release\
-
+
diff --git a/Mixins/ActionGroups/ActionSequence.cs b/Mixins/ActionGroups/ActionSequence.cs
index 15f7b23..acf03be 100644
--- a/Mixins/ActionGroups/ActionSequence.cs
+++ b/Mixins/ActionGroups/ActionSequence.cs
@@ -14,16 +14,16 @@ namespace IngameScript
public string Name { get; private set; }
public bool Running { get; private set; } = false;
- private SortedDictionary> _steps = new SortedDictionary>();
+ private SortedDictionary> _steps = new SortedDictionary>();
public ActionSequence(string name)
{
Name = name;
}
- public void Add(int step, IBlockAction action)
+ public void Add(int step, BlockAction action)
{
- if (!_steps.ContainsKey(step)) _steps[step] = new List();
+ if (!_steps.ContainsKey(step)) _steps[step] = new List();
_steps[step].Add(action);
}
@@ -33,9 +33,9 @@ namespace IngameScript
Running = true;
List> jobs = new List>();
- foreach (List step in _steps.Values)
+ foreach (List step in _steps.Values)
{
- foreach (IBlockAction action in step)
+ foreach (BlockAction action in step)
{
jobs.Add(action.Run());
}
diff --git a/Mixins/ActionGroups/BlockAction.cs b/Mixins/ActionGroups/BlockAction.cs
new file mode 100644
index 0000000..a4ebff3
--- /dev/null
+++ b/Mixins/ActionGroups/BlockAction.cs
@@ -0,0 +1,29 @@
+// An interface to represent a pre-configured action performed asynchronously
+// on a block. Implements a Run() method that executes the action and provides an
+// Enumerator to monitor when the action is complete.
+
+using System.Collections.Generic;
+
+namespace IngameScript
+{
+ partial class Program
+ {
+ public abstract class BlockAction
+ {
+ public bool Running { get; private set; } = false;
+
+ public IEnumerator Run()
+ {
+ if (Running) yield break;
+ Running = true;
+
+ IEnumerator childRun = onRun();
+ while (childRun.MoveNext()) yield return true;
+
+ Running = false;
+ }
+
+ protected abstract IEnumerator onRun();
+ }
+ }
+}
\ No newline at end of file
diff --git a/Mixins/ActionGroups/BlockActionConnector.cs b/Mixins/ActionGroups/BlockActionConnector.cs
new file mode 100644
index 0000000..634f6c6
--- /dev/null
+++ b/Mixins/ActionGroups/BlockActionConnector.cs
@@ -0,0 +1,44 @@
+using System.Collections.Generic;
+using Sandbox.ModAPI.Ingame;
+
+namespace IngameScript
+{
+ partial class Program
+ {
+ public enum ConnectorAction
+ {
+ Connect,
+ Disconnect,
+ }
+
+ public class BlockActionConnector : BlockAction
+ {
+ private IMyShipConnector _connector;
+ private ConnectorAction _action;
+
+ public BlockActionConnector(
+ IMyShipConnector connector,
+ ConnectorAction action
+ )
+ {
+ _connector = connector;
+ _action = action;
+ }
+
+ protected override IEnumerator onRun()
+ {
+ switch (_action)
+ {
+ case ConnectorAction.Connect:
+ _connector.Connect();
+ while (_connector.Status != MyShipConnectorStatus.Connected) yield return true;
+ break;
+ case ConnectorAction.Disconnect:
+ _connector.Disconnect();
+ while (_connector.Status == MyShipConnectorStatus.Connected) yield return true;
+ break;
+ }
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/Mixins/ActionGroups/BlockActionDoor.cs b/Mixins/ActionGroups/BlockActionDoor.cs
index 300b014..f71246b 100644
--- a/Mixins/ActionGroups/BlockActionDoor.cs
+++ b/Mixins/ActionGroups/BlockActionDoor.cs
@@ -5,16 +5,14 @@ namespace IngameScript
{
partial class Program
{
- public class BlockActionDoor : IBlockAction
+ public enum DoorAction
{
- public enum DoorAction
- {
- Open,
- Close,
- }
-
- public bool Running { get; private set; } = false;
+ Open,
+ Close,
+ }
+ public class BlockActionDoor : BlockAction
+ {
private IMyDoor _door;
private DoorAction _action;
private bool _lockDoor;
@@ -30,7 +28,7 @@ namespace IngameScript
_lockDoor = lockDoor;
}
- public IEnumerator Run()
+ protected override IEnumerator onRun()
{
switch (_action)
{
diff --git a/Mixins/ActionGroups/BlockActionGasTank.cs b/Mixins/ActionGroups/BlockActionGasTank.cs
new file mode 100644
index 0000000..5595777
--- /dev/null
+++ b/Mixins/ActionGroups/BlockActionGasTank.cs
@@ -0,0 +1,43 @@
+using System.Collections.Generic;
+using Sandbox.ModAPI.Ingame;
+
+namespace IngameScript
+{
+ partial class Program
+ {
+ public enum GasTankAction
+ {
+ Stockpile,
+ Dispense,
+ }
+
+ public class BlockActionGasTank : BlockAction
+ {
+ private IMyGasTank _gasTank;
+ private GasTankAction _action;
+
+ public BlockActionGasTank(
+ IMyGasTank gasTank,
+ GasTankAction action
+ )
+ {
+ _gasTank = gasTank;
+ _action = action;
+ }
+
+ protected override IEnumerator onRun()
+ {
+ switch (_action)
+ {
+ case GasTankAction.Stockpile:
+ _gasTank.Stockpile = true;
+ break;
+ case GasTankAction.Dispense:
+ _gasTank.Stockpile = false;
+ break;
+ }
+ yield return true;
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/Mixins/ActionGroups/BlockActionPiston.cs b/Mixins/ActionGroups/BlockActionPiston.cs
index 45a8778..22d016c 100644
--- a/Mixins/ActionGroups/BlockActionPiston.cs
+++ b/Mixins/ActionGroups/BlockActionPiston.cs
@@ -5,7 +5,7 @@ namespace IngameScript
{
partial class Program
{
- public class BlockActionPiston : IBlockAction
+ public class BlockActionPiston : BlockAction
{
public bool Running { get; private set; } = false;
diff --git a/Mixins/ActionGroups/BlockActionRotor.cs b/Mixins/ActionGroups/BlockActionRotor.cs
index f752932..d0458d9 100644
--- a/Mixins/ActionGroups/BlockActionRotor.cs
+++ b/Mixins/ActionGroups/BlockActionRotor.cs
@@ -5,7 +5,7 @@ namespace IngameScript
{
partial class Program
{
- public class BlockActionRotor : IBlockAction
+ public class BlockActionRotor : BlockAction
{
public bool Running { get; private set; } = false;
diff --git a/Mixins/ActionGroups/BlockActionThruster.cs b/Mixins/ActionGroups/BlockActionThruster.cs
new file mode 100644
index 0000000..74e6671
--- /dev/null
+++ b/Mixins/ActionGroups/BlockActionThruster.cs
@@ -0,0 +1,43 @@
+using System.Collections.Generic;
+using Sandbox.ModAPI.Ingame;
+
+namespace IngameScript
+{
+ partial class Program
+ {
+ public enum ThrusterAction
+ {
+ Enable,
+ Disable,
+ }
+
+ public class BlockActionThruster : BlockAction
+ {
+ private IMyThrust _thruster;
+ private ThrusterAction _action;
+
+ public BlockActionThruster(
+ IMyThrust thruster,
+ ThrusterAction action
+ )
+ {
+ _thruster = thruster;
+ _action = action;
+ }
+
+ protected override IEnumerator onRun()
+ {
+ switch (_action)
+ {
+ case ThrusterAction.Enable:
+ _thruster.Enabled = true;
+ break;
+ case ThrusterAction.Disable:
+ _thruster.Enabled = false;
+ break;
+ }
+ yield return true;
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/Mixins/ActionGroups/IBlockAction.cs b/Mixins/ActionGroups/IBlockAction.cs
deleted file mode 100644
index 5b05de5..0000000
--- a/Mixins/ActionGroups/IBlockAction.cs
+++ /dev/null
@@ -1,17 +0,0 @@
-// An interface to represent a pre-configured action performed asynchronously
-// on a block. Implements a Run() method that executes the action and provides an
-// Enumerator to monitor when the action is complete.
-
-using System.Collections.Generic;
-
-namespace IngameScript
-{
- partial class Program
- {
- public interface IBlockAction
- {
- bool Running { get; }
- IEnumerator Run();
- }
- }
-}
\ No newline at end of file
diff --git a/SpaceEngineers.sln b/SpaceEngineers.sln
index f7334d0..700cf5e 100644
--- a/SpaceEngineers.sln
+++ b/SpaceEngineers.sln
@@ -13,6 +13,8 @@ Project("{8A3CDCC5-4B55-4D87-A415-698A0E1FF06F}") = "ActionGroups", "Mixins\Acti
EndProject
Project("{8A3CDCC5-4B55-4D87-A415-698A0E1FF06F}") = "Console", "Mixins\Console\Console.shproj", "{323E8400-84C2-46A0-B2E9-FCD3B31681DA}"
EndProject
+Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "DockingController", "DockingController\DockingController.csproj", "{FDF834C0-D680-4FFA-8238-FE1FBDCF5B9D}"
+EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
@@ -31,6 +33,10 @@ Global
{40B352CD-100E-4F87-A7A0-FF00F4B8846C}.Debug|Any CPU.Build.0 = Debug|x64
{40B352CD-100E-4F87-A7A0-FF00F4B8846C}.Release|Any CPU.ActiveCfg = Release|x64
{40B352CD-100E-4F87-A7A0-FF00F4B8846C}.Release|Any CPU.Build.0 = Release|x64
+ {FDF834C0-D680-4FFA-8238-FE1FBDCF5B9D}.Debug|Any CPU.ActiveCfg = Debug|x64
+ {FDF834C0-D680-4FFA-8238-FE1FBDCF5B9D}.Debug|Any CPU.Build.0 = Debug|x64
+ {FDF834C0-D680-4FFA-8238-FE1FBDCF5B9D}.Release|Any CPU.ActiveCfg = Release|x64
+ {FDF834C0-D680-4FFA-8238-FE1FBDCF5B9D}.Release|Any CPU.Build.0 = Release|x64
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE