INSA
  • Tutorials
  • Documentation
  • Api Documentation
  • Changelog
Show / Hide Table of Contents
  • Getting Started
    • Quickstart
  • Unity tutorial
    • Introduction
    • Time for practice
    • Restricted scenario by script?
    • How to create the tutorial scene?
  • Scenario
    • How to create a sensor?
    • How to create an effector?
    • How to setup the engine?
    • How to edit a scenario?
    • How to run a scenario?
    • How to?
  • Relation engine
    • How to create a type?
    • How to create a relation?
    • What are queries? How do queries work?
    • How to be notified when a relation is executed?
  • Highlight Manager
    • How to create a Highlight?

How do queries work ?

The relation engine knows all types, objects and relations that are registered to it. Queries are a way to extract data from the relation engine (which is actually the whole point of the relation engine). There are two types of queries :

  • Object queries are used to find one or multiple objects that contain specific types (i.e. all objects that are grabbable and screwers)
  • Realization queries are used to know which realization (meaning, actions or relation implementation) match given sets of objects and available relations.

Queries can be launched either directly or asynchronously. In the later case, the query is launched in a separate thread and the provided callback method is called when the result is available.

Note

You can check the RelationEngineQueries sample project

Create and launch an object query

The first step is to create an ObjectQueryParameters either from scratch or through a prefilled method like GetQueryAllObjects(IEngine)

The second step is to tweak the query parameters content by adding/removing objects that the query will look into and adding/removing types that the resulting objects must have.

When the query parameters are all set, the query can be launched using the relation engine. In unity this is done by calling one of the GetObjects(ObjectQueryParameters, Action<List<IObject>>, bool) methods. You can launch multiple queries at once and specify a callback @System.Action if you want the query to run asynchronously

using System.Collections.Generic;

using UnityEngine;

using Xareus.Relations;
using Xareus.Relations.Unity;

namespace Xareus.Samples.RelationEngineQueries
{
    /// <summary>
    /// This class shows examples of how to query the Relation Engine for objects
    /// </summary>
    public class ObjectQueryExample : MonoBehaviour
    {
        #region Fields

        public List<XUObject> ObjectsTheQueryWillLookInto;

        #endregion

        #region Methods

        /// <summary>
        /// This method will be called at the next Unity Update step when the query is done
        /// </summary>
        public static void ResultCallback(IEnumerable<IObject> objects)
        {
            string resultString = string.Join(", ", objects);
            Debug.Log("Async Query Result: " + resultString);
        }

        /// <summary>
        /// Query the Relation Engine for all possible realizations and call the callback when the query is done
        /// </summary>
        private void AsyncrhonousQuery()
        {
            ObjectQueryParameters directQueryParameters = ObjectQueryParameters.GetQueryAllObjects(RelationEngine.Instance.Engine);

            // Create a type search and assign its parameters
            TypeSearch typeSearch = new()
            {
                Type = new Type(typeof(SampleType)),
                // Every object that holds the type TestType exactly once
                MinOccurs = 1,
                MaxOccurs = 1
            };

            directQueryParameters.TypesToHave.Add(typeSearch);

            RelationEngine.Instance.GetObjects(directQueryParameters, ResultCallback);
        }

        private void Start()
        {
            DirectQuery();
            AsyncrhonousQuery();
        }

        /// <summary>
        /// Query the Relation Engine for all possible realizations (blocking the main thread)
        /// </summary>
        private void DirectQuery()
        {
            ObjectQueryParameters directQueryParameters = new();
            foreach (XUObject xuObject in ObjectsTheQueryWillLookInto)
                directQueryParameters.ObjectsToLookInto.Add(xuObject);

            // Create a type search and assign its parameters
            TypeSearch typeSearch = new()
            {
                Type = new Type(typeof(SampleType)),
                // Every object that holds the type TestType once or twice will be returned
                MinOccurs = 1,
                MaxOccurs = 2
            };

            directQueryParameters.TypesToHave.Add(typeSearch);

            List<IObject> directResult = RelationEngine.Instance.GetObjects(directQueryParameters);

            string resultString = string.Join(", ", directResult);
            Debug.Log("Direct Query Result: " + resultString);
        }

        #endregion
    }
}

Create and launch a realization query

The first step is to create a RealizationQueryParameters either from scratch or through a prefilled methods like GetQueryAllOptionalAllRelation(IEngine), GetQueryAllOptional(IEngine) or GetQueryAllRelation(IEngine)

The second step is to tweak the query parameters content by adding/removing mandatory and optional objects or object types that the query will look into and adding/removing relations that will be considered.

When the query parameters are all set, the query can be launched using the relation engine. In unity this is done by calling one of the GetRealizations(RealizationQueryParameters, Action<List<XURealization>>, bool) methods. You can launch multiple queries at once and specify a callback @System.Action if you want the query to run asynchronously to prevent blocking unity's main thread for example.

using System.Collections.Generic;

using UnityEngine;

using Xareus.Relations;
using Xareus.Relations.Unity;

namespace Xareus.Samples.RelationEngineQueries
{
    /// <summary>
    /// This class shows examples of how to query the Relation Engine for realizations
    /// </summary>
    public class RealizationQueryExample : MonoBehaviour
    {
        #region Fields

        public List<XUObject> MandatoryObjects;
        public List<XUObject> OptionalObjects;
        public List<XURelation> Relations;

        #endregion

        #region Methods

        /// <summary>
        /// This method will be called at the next Unity Update step when the query is done
        /// </summary>
        public static void ResultCallback(IEnumerable<XURealization> realizations)
        {
            string resultString = string.Join(", ", realizations);
            Debug.Log("Async Query Result: " + resultString);
        }

        /// <summary>
        /// Query the Relation Engine for all possible realizations and call the callback when the query is done
        /// </summary>
        private static void AsyncrhonousQuery()
        {
            // This will query all possible realization in the scene
            RealizationQueryParameters directQueryParameters = RealizationQueryParameters.GetQueryAllOptionalAllRelation(RelationEngine.Instance.Engine);

            RelationEngine.Instance.GetRealizations(directQueryParameters, ResultCallback);
        }

        private void Start()
        {
            DirectQuery();
            AsyncrhonousQuery();
        }

        /// <summary>
        /// Query the Relation Engine for all possible realizations (blocking the main thread)
        /// </summary>
        private void DirectQuery()
        {
            RealizationQueryParameters directQueryParameters = new();

            // The mandatory objects must be present in the result
            foreach (XUObject xuObject in MandatoryObjects)
                directQueryParameters.MandatoryObjects.Add(xuObject);

            // The optional objects may be present in the result
            foreach (XUObject xuObject in OptionalObjects)
                directQueryParameters.OptionalObjects.Add(xuObject);

            foreach (XURelation relation in Relations)
                directQueryParameters.RelationsToUse.Add(relation);

            List<XURealization> directResult = RelationEngine.Instance.GetRealizations(directQueryParameters);

            string resultString = string.Join(", ", directResult);
            Debug.Log("Direct Query Result: " + resultString);
        }

        #endregion
    }
}
INSA     IRISA     Inria     Ouest Valorisation Back to top