using System; using System.Collections.Generic; using System.Linq; using Content.Server.Chemistry.Components.SolutionManager; using Content.Server.Mind.Components; using Content.Server.Power.Components; using Content.Shared.Tag; using Robust.Server.Bql; using Robust.Shared.GameObjects; namespace Content.Server.Bql { public class QuerySelectors { [RegisterBqlQuerySelector] public class MindfulQuerySelector : BqlQuerySelector { public override string Token => "mindful"; public override QuerySelectorArgument[] Arguments => Array.Empty(); public override IEnumerable DoSelection(IEnumerable input, IReadOnlyList arguments, bool isInverted, IEntityManager entityManager) { return input.Where(e => { if (entityManager.TryGetComponent(e, out var mind)) return (mind.Mind?.VisitingEntity == e) ^ isInverted; return isInverted; }); } public override IEnumerable DoInitialSelection(IReadOnlyList arguments, bool isInverted, IEntityManager entityManager) { return DoSelection( entityManager.EntityQuery().Select(x => x.Owner), arguments, isInverted, entityManager); } } [RegisterBqlQuerySelector] public class TaggedQuerySelector : BqlQuerySelector { public override string Token => "tagged"; public override QuerySelectorArgument[] Arguments => new [] { QuerySelectorArgument.String }; public override IEnumerable DoSelection(IEnumerable input, IReadOnlyList arguments, bool isInverted, IEntityManager entityManager) { return input.Where(e => (entityManager.TryGetComponent(e, out var tag) && tag.Tags.Contains((string) arguments[0])) ^ isInverted); } public override IEnumerable DoInitialSelection(IReadOnlyList arguments, bool isInverted, IEntityManager entityManager) { return DoSelection(entityManager.EntityQuery().Select(x => x.Owner), arguments, isInverted, entityManager); } } [RegisterBqlQuerySelector] public class AliveQuerySelector : BqlQuerySelector { public override string Token => "alive"; public override QuerySelectorArgument[] Arguments => Array.Empty(); public override IEnumerable DoSelection(IEnumerable input, IReadOnlyList arguments, bool isInverted, IEntityManager entityManager) { return input.Where(e => (entityManager.TryGetComponent(e, out var mind) && !(mind.Mind?.CharacterDeadPhysically ?? false)) ^ isInverted); } public override IEnumerable DoInitialSelection(IReadOnlyList arguments, bool isInverted, IEntityManager entityManager) { return DoSelection(entityManager.EntityQuery().Select(x => x.Owner), arguments, isInverted, entityManager); } } [RegisterBqlQuerySelector] public class HasReagentQuerySelector : BqlQuerySelector { public override string Token => "hasreagent"; public override QuerySelectorArgument[] Arguments => new [] { QuerySelectorArgument.String }; public override IEnumerable DoSelection(IEnumerable input, IReadOnlyList arguments, bool isInverted, IEntityManager entityManager) { var reagent = (string) arguments[0]; return input.Where(e => { if (entityManager.TryGetComponent(e, out var solutionContainerManagerComponent)) { return solutionContainerManagerComponent.Solutions .Any(solution => solution.Value.ContainsReagent(reagent)) ^ isInverted; } return isInverted; }); } public override IEnumerable DoInitialSelection(IReadOnlyList arguments, bool isInverted, IEntityManager entityManager) { return DoSelection(entityManager.EntityQuery().Select(x => x.Owner), arguments, isInverted, entityManager); } } [RegisterBqlQuerySelector] public class ApcPoweredQuerySelector : BqlQuerySelector { public override string Token => "apcpowered"; public override QuerySelectorArgument[] Arguments => Array.Empty(); public override IEnumerable DoSelection(IEnumerable input, IReadOnlyList arguments, bool isInverted, IEntityManager entityManager) { return input.Where(e => entityManager.TryGetComponent(e, out var apcPowerReceiver) ? apcPowerReceiver.Powered ^ isInverted : isInverted); } public override IEnumerable DoInitialSelection(IReadOnlyList arguments, bool isInverted, IEntityManager entityManager) { return DoSelection(entityManager.EntityQuery().Select(x => x.Owner), arguments, isInverted, entityManager); } } } }