using Sandbox.ModAPI.Ingame;
using SpaceEngineers.Game.ModAPI.Ingame;
using System.Collections.Generic;
using VRage.Game.ModAPI.Ingame.Utilities;

namespace IngameScript
{
    partial class Program
    {
        public class AirZone
        {
            public bool Triggered = false;

            private MyIni _ini;
            private List<IMyAirVent> _vents;
            private PrefixedConsole _console;
            private Sequencer _sequencer;
            private const float TriggerLevel = 0.75F;

            public AirZone(string zoneName, MyIni ini, IConsole console)
            {
                _ini = ini;
                _console = new PrefixedConsole(console, zoneName);
                _sequencer = new Sequencer(zoneName, _console);
                _vents = new List<IMyAirVent>();
            }

            public void AddBlock(IMyTerminalBlock block)
            {
                if (block is IMyAirVent)
                {
                    _vents.Add(block as IMyAirVent);
                }
                else if (block is IMyDoor)
                {
                    SequenceableDoor wrapped = SequenceableFactory.MakeSequenceable(block as IMyDoor, _ini, "airMonitor") as SequenceableDoor;
                    wrapped.Step = 0;
                    wrapped.DeployOpen = false;
                    wrapped.LockOpen = false;
                    wrapped.LockClosed = true;
                    _sequencer.AddBlock(wrapped);
                }
                else
                {
                    _console.Print("Tried to add incompatible block '{block.CustomName}'");
                }
                // TODO: support for arbitrary (sub-)sequences here could be powerful
            }

            // This enumerator should run forever.
            public IEnumerator<bool> Monitor()
            {
                while (true)
                {
                    foreach (IMyAirVent vent in _vents)
                    {
                        if (vent.GetOxygenLevel() < TriggerLevel) Triggered = true;
                    }

                    if (Triggered == true)
                    {
                        // close the doors
                        IEnumerator<bool> job = _sequencer.RunSequence(true);
                        while (job.MoveNext()) yield return true;

                        // noop until manually reset
                        while (Triggered) yield return true;

                        // open the doors
                        job = _sequencer.RunSequence(false);
                        while (job.MoveNext()) yield return true;
                    }

                    yield return true;
                }
            }
        }
    }
}