浏览代码

Separate grid sensor and component (#5209)

/check-for-ModelOverriders
GitHub 3 年前
当前提交
3fbcc26c
共有 18 个文件被更改,包括 1253 次插入1005 次删除
  1. 342
      Project/Assets/ML-Agents/Examples/FoodCollector/Prefabs/FoodCollectorArea.prefab
  2. 245
      Project/Assets/ML-Agents/Examples/FoodCollector/Scenes/FoodCollector.unity
  3. 693
      com.unity.ml-agents.extensions/Runtime/Sensors/GridSensor.cs
  4. 2
      com.unity.ml-agents.extensions/Runtime/Sensors/GridSensorComponent.cs.meta
  5. 128
      com.unity.ml-agents.extensions/Tests/Editor/Sensors/ChannelHotPerceiveTests.cs
  6. 20
      com.unity.ml-agents.extensions/Tests/Editor/Sensors/ChannelHotShapeTests.cs
  7. 128
      com.unity.ml-agents.extensions/Tests/Editor/Sensors/ChannelPerceiveTests.cs
  8. 16
      com.unity.ml-agents.extensions/Tests/Editor/Sensors/ChannelShapeTests.cs
  9. 45
      com.unity.ml-agents.extensions/Tests/Editor/Sensors/CountingGridSensorPerceiveTests.cs
  10. 8
      com.unity.ml-agents.extensions/Tests/Editor/Sensors/CountingGridSensorShapeTests.cs
  11. 35
      com.unity.ml-agents.extensions/Tests/Editor/Sensors/GridObservationPerceiveTests.cs
  12. 14
      com.unity.ml-agents.extensions/Tests/Editor/Sensors/GridSensorTestUtils.cs
  13. 50
      com.unity.ml-agents.extensions/Tests/Utils/GridObsTestComponents/SimpleTestGridSensor.cs
  14. 121
      com.unity.ml-agents.extensions/Editor/GridSensorComponentEditor.cs
  15. 11
      com.unity.ml-agents.extensions/Editor/GridSensorComponentEditor.cs.meta
  16. 286
      com.unity.ml-agents.extensions/Runtime/Sensors/GridSensorComponent.cs
  17. 114
      com.unity.ml-agents.extensions/Runtime/Sensors/CountingGridSensor.cs
  18. 0
      /com.unity.ml-agents.extensions/Runtime/Sensors/GridSensorComponent.cs.meta

342
Project/Assets/ML-Agents/Examples/FoodCollector/Prefabs/FoodCollectorArea.prefab


m_ClearFlags: 2
m_BackGroundColor: {r: 0.46666667, g: 0.5647059, b: 0.60784316, a: 1}
m_projectionMatrixMode: 1
m_GateFitMode: 2
m_FOVAxisMode: 0
m_GateFitMode: 2
m_FocalLength: 50
m_NormalizedViewPortRect:
serializedVersion: 2

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_ClearFlags: 2
m_BackGroundColor: {r: 0.46666667, g: 0.5647059, b: 0.60784316, a: 1}
m_projectionMatrixMode: 1
m_GateFitMode: 2
m_FOVAxisMode: 0
m_GateFitMode: 2
m_FocalLength: 50
m_NormalizedViewPortRect:
serializedVersion: 2

m_ClearFlags: 2
m_BackGroundColor: {r: 0.46666667, g: 0.5647059, b: 0.60784316, a: 1}
m_projectionMatrixMode: 1
m_GateFitMode: 2
m_FOVAxisMode: 0
m_GateFitMode: 2
m_FocalLength: 50
m_NormalizedViewPortRect:
serializedVersion: 2

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 0
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 0
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_Material: {fileID: 0}
m_IsTrigger: 0
m_Enabled: 1
serializedVersion: 3
serializedVersion: 4
m_CookingOptions: 14
m_CookingOptions: 30
m_Mesh: {fileID: 4300000, guid: a9d8f499f5b9848438d280dc28b3b52e, type: 3}
--- !u!1 &1464820575638702
GameObject:

- component: {fileID: 114176228333253036}
- component: {fileID: 8297075921230369060}
- component: {fileID: 1222199865870203693}
- component: {fileID: 6035497842152854922}
- component: {fileID: 2010492400}
m_Layer: 0
m_Name: Agent
m_TagString: agent

m_Name:
m_EditorClassIdentifier:
debugCommandLineOverride:
--- !u!114 &6035497842152854922
--- !u!114 &2010492400
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}

m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: 801669c0cdece6b40b2e741ad0b119ac, type: 3}
m_Script: {fileID: 11500000, guid: 2a501962d056745d1a30e99146ee39fe, type: 3}
Name:
CellScaleX: 1
CellScaleZ: 1
GridNumSideX: 40
GridNumSideZ: 40
CellScaleY: 0.01
RotateToAgent: 1
ChannelDepth: 06000000
DetectableObjects:
m_SensorName: GridSensor
m_CellScale: {x: 1, y: 0.01, z: 1}
m_GridNumSide: {x: 40, y: 1, z: 40}
m_RotateWithAgent: 1
m_ChannelDepth: 06000000
m_DetectableObjects:
ObserveMask:
m_ObserveMask:
gridDepthType: 1
rootReference: {fileID: 0}
ObservationPerCell: 0
NumberOfObservations: 0
ChannelOffsets:
DebugColors:
- {r: 0.4039216, g: 0.7372549, b: 0.41960788, a: 0}
- {r: 0.12941177, g: 0.5882353, b: 0.95294124, a: 0}
- {r: 0.3921569, g: 0.3921569, b: 0.3921569, a: 0}
- {r: 0.74509805, g: 0.227451, b: 0.15294118, a: 0}
m_DepthType: 1
m_RootReference: {fileID: 0}
m_MaxColliderBufferSize: 500
m_InitialColliderBufferSize: 4
m_DebugColors:
- {r: 0.40392157, g: 0.7372549, b: 0.41960785, a: 0}
- {r: 0.12941177, g: 0.5882353, b: 0.9529412, a: 0}
- {r: 0.39215687, g: 0.39215687, b: 0.39215687, a: 0}
- {r: 0.74509805, g: 0.22745098, b: 0.15294118, a: 0}
GizmoYOffset: 0
ShowGizmos: 0
CompressionType: 1
m_GizmoYOffset: 0
m_ShowGizmos: 0
m_CompressionType: 1
m_ObservationStacks: 1
--- !u!1 &1482701732800114
GameObject:
m_ObjectHideFlags: 0

m_ClearFlags: 2
m_BackGroundColor: {r: 0.46666667, g: 0.5647059, b: 0.60784316, a: 1}
m_projectionMatrixMode: 1
m_GateFitMode: 2
m_FOVAxisMode: 0
m_GateFitMode: 2
m_FocalLength: 50
m_NormalizedViewPortRect:
serializedVersion: 2

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

- component: {fileID: 114522573150607728}
- component: {fileID: 114711827726849508}
- component: {fileID: 259154752087955944}
- component: {fileID: 3067525015186813280}
- component: {fileID: 7409303125559953495}
m_Layer: 0
m_Name: Agent (1)
m_TagString: agent

m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 1495617568563208}
m_LocalRotation: {x: -0, y: -0, z: -0, w: 1}
m_LocalPosition: {x: -34.2, y: 2, z: -9.559753}
m_LocalPosition: {x: -34.2, y: 2, z: -9.9}
m_LocalScale: {x: 1, y: 1, z: 1}
m_Children:
- {fileID: 4343281584596502}

m_EditorClassIdentifier:
DecisionPeriod: 5
TakeActionsBetweenDecisions: 1
--- !u!114 &3067525015186813280
--- !u!114 &7409303125559953495
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}

m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: 801669c0cdece6b40b2e741ad0b119ac, type: 3}
m_Script: {fileID: 11500000, guid: 2a501962d056745d1a30e99146ee39fe, type: 3}
Name:
CellScaleX: 1
CellScaleZ: 1
GridNumSideX: 40
GridNumSideZ: 40
CellScaleY: 0.01
RotateToAgent: 1
ChannelDepth: 06000000
DetectableObjects:
m_SensorName: GridSensor
m_CellScale: {x: 1, y: 0.01, z: 1}
m_GridNumSide: {x: 40, y: 1, z: 40}
m_RotateWithAgent: 1
m_ChannelDepth: 06000000
m_DetectableObjects:
ObserveMask:
m_ObserveMask:
gridDepthType: 1
rootReference: {fileID: 0}
ObservationPerCell: 0
NumberOfObservations: 0
ChannelOffsets:
DebugColors:
- {r: 0.4039216, g: 0.7372549, b: 0.41960788, a: 0}
- {r: 0.12941177, g: 0.5882353, b: 0.95294124, a: 0}
- {r: 0.3921569, g: 0.3921569, b: 0.3921569, a: 0}
- {r: 0.74509805, g: 0.227451, b: 0.15294118, a: 0}
m_DepthType: 1
m_RootReference: {fileID: 0}
m_MaxColliderBufferSize: 500
m_InitialColliderBufferSize: 4
m_DebugColors:
- {r: 0.40392157, g: 0.7372549, b: 0.41960785, a: 0}
- {r: 0.12941177, g: 0.5882353, b: 0.9529412, a: 0}
- {r: 0.39215687, g: 0.39215687, b: 0.39215687, a: 0}
- {r: 0.74509805, g: 0.22745098, b: 0.15294118, a: 0}
GizmoYOffset: 0
ShowGizmos: 0
CompressionType: 1
m_GizmoYOffset: 0
m_ShowGizmos: 0
m_CompressionType: 1
m_ObservationStacks: 1
--- !u!1 &1528397385587768
GameObject:
m_ObjectHideFlags: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

- component: {fileID: 114980787530065684}
- component: {fileID: 114542632553128056}
- component: {fileID: 5519119940433428255}
- component: {fileID: 8466013622553267624}
- component: {fileID: 1115669858669834387}
m_Layer: 0
m_Name: Agent (2)
m_TagString: agent

m_EditorClassIdentifier:
DecisionPeriod: 5
TakeActionsBetweenDecisions: 1
--- !u!114 &8466013622553267624
--- !u!114 &1115669858669834387
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}

m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: 801669c0cdece6b40b2e741ad0b119ac, type: 3}
m_Script: {fileID: 11500000, guid: 2a501962d056745d1a30e99146ee39fe, type: 3}
Name:
CellScaleX: 1
CellScaleZ: 1
GridNumSideX: 40
GridNumSideZ: 40
CellScaleY: 0.01
RotateToAgent: 1
ChannelDepth: 06000000
DetectableObjects:
m_SensorName: GridSensor
m_CellScale: {x: 1, y: 0.01, z: 1}
m_GridNumSide: {x: 40, y: 1, z: 40}
m_RotateWithAgent: 1
m_ChannelDepth: 06000000
m_DetectableObjects:
ObserveMask:
m_ObserveMask:
gridDepthType: 1
rootReference: {fileID: 0}
ObservationPerCell: 0
NumberOfObservations: 0
ChannelOffsets:
DebugColors:
- {r: 0.4039216, g: 0.7372549, b: 0.41960788, a: 0}
- {r: 0.12941177, g: 0.5882353, b: 0.95294124, a: 0}
- {r: 0.3921569, g: 0.3921569, b: 0.3921569, a: 0}
- {r: 0.74509805, g: 0.227451, b: 0.15294118, a: 0}
m_DepthType: 1
m_RootReference: {fileID: 0}
m_MaxColliderBufferSize: 500
m_InitialColliderBufferSize: 4
m_DebugColors:
- {r: 0.40392157, g: 0.7372549, b: 0.41960785, a: 0}
- {r: 0.12941177, g: 0.5882353, b: 0.9529412, a: 0}
- {r: 0.39215687, g: 0.39215687, b: 0.39215687, a: 0}
- {r: 0.74509805, g: 0.22745098, b: 0.15294118, a: 0}
GizmoYOffset: 0
ShowGizmos: 0
CompressionType: 1
m_GizmoYOffset: 0
m_ShowGizmos: 0
m_CompressionType: 1
m_ObservationStacks: 1
--- !u!1 &1617924810425504
GameObject:
m_ObjectHideFlags: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

- component: {fileID: 114878550018296316}
- component: {fileID: 114189751434580810}
- component: {fileID: 5884750436653390196}
- component: {fileID: 6247312751399400490}
- component: {fileID: 3147256093106034163}
m_Layer: 0
m_Name: Agent (4)
m_TagString: agent

m_EditorClassIdentifier:
DecisionPeriod: 5
TakeActionsBetweenDecisions: 1
--- !u!114 &6247312751399400490
--- !u!114 &3147256093106034163
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}

m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: 801669c0cdece6b40b2e741ad0b119ac, type: 3}
m_Script: {fileID: 11500000, guid: 2a501962d056745d1a30e99146ee39fe, type: 3}
Name:
CellScaleX: 1
CellScaleZ: 1
GridNumSideX: 40
GridNumSideZ: 40
CellScaleY: 0.01
RotateToAgent: 1
ChannelDepth: 06000000
DetectableObjects:
m_SensorName: GridSensor
m_CellScale: {x: 1, y: 0.01, z: 1}
m_GridNumSide: {x: 40, y: 1, z: 40}
m_RotateWithAgent: 1
m_ChannelDepth: 06000000
m_DetectableObjects:
ObserveMask:
m_ObserveMask:
gridDepthType: 1
rootReference: {fileID: 0}
ObservationPerCell: 0
NumberOfObservations: 0
ChannelOffsets:
DebugColors:
- {r: 0.4039216, g: 0.7372549, b: 0.41960788, a: 0}
- {r: 0.12941177, g: 0.5882353, b: 0.95294124, a: 0}
- {r: 0.3921569, g: 0.3921569, b: 0.3921569, a: 0}
- {r: 0.74509805, g: 0.227451, b: 0.15294118, a: 0}
m_DepthType: 1
m_RootReference: {fileID: 0}
m_MaxColliderBufferSize: 500
m_InitialColliderBufferSize: 4
m_DebugColors:
- {r: 0.40392157, g: 0.7372549, b: 0.41960785, a: 0}
- {r: 0.12941177, g: 0.5882353, b: 0.9529412, a: 0}
- {r: 0.39215687, g: 0.39215687, b: 0.39215687, a: 0}
- {r: 0.74509805, g: 0.22745098, b: 0.15294118, a: 0}
GizmoYOffset: 0
ShowGizmos: 0
CompressionType: 1
m_GizmoYOffset: 0
m_ShowGizmos: 0
m_CompressionType: 1
m_ObservationStacks: 1
--- !u!1 &1688105343773098
GameObject:
m_ObjectHideFlags: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

- component: {fileID: 114035338027591536}
- component: {fileID: 114235147148547996}
- component: {fileID: 4768752321433982785}
- component: {fileID: 5837508007780682603}
- component: {fileID: 3712017990468381030}
m_Layer: 0
m_Name: Agent (3)
m_TagString: agent

m_EditorClassIdentifier:
DecisionPeriod: 5
TakeActionsBetweenDecisions: 1
--- !u!114 &5837508007780682603
--- !u!114 &3712017990468381030
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}

m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: 801669c0cdece6b40b2e741ad0b119ac, type: 3}
m_Script: {fileID: 11500000, guid: 2a501962d056745d1a30e99146ee39fe, type: 3}
Name:
CellScaleX: 1
CellScaleZ: 1
GridNumSideX: 40
GridNumSideZ: 40
CellScaleY: 0.01
RotateToAgent: 1
ChannelDepth: 06000000
DetectableObjects:
m_SensorName: GridSensor
m_CellScale: {x: 1, y: 0.01, z: 1}
m_GridNumSide: {x: 40, y: 1, z: 40}
m_RotateWithAgent: 1
m_ChannelDepth: 06000000
m_DetectableObjects:
ObserveMask:
m_ObserveMask:
gridDepthType: 1
rootReference: {fileID: 0}
ObservationPerCell: 0
NumberOfObservations: 0
ChannelOffsets:
DebugColors:
- {r: 0.4039216, g: 0.7372549, b: 0.41960788, a: 0}
- {r: 0.12941177, g: 0.5882353, b: 0.95294124, a: 0}
- {r: 0.3921569, g: 0.3921569, b: 0.3921569, a: 0}
- {r: 0.74509805, g: 0.227451, b: 0.15294118, a: 0}
m_DepthType: 1
m_RootReference: {fileID: 0}
m_MaxColliderBufferSize: 500
m_InitialColliderBufferSize: 4
m_DebugColors:
- {r: 0.40392157, g: 0.7372549, b: 0.41960785, a: 0}
- {r: 0.12941177, g: 0.5882353, b: 0.9529412, a: 0}
- {r: 0.39215687, g: 0.39215687, b: 0.39215687, a: 0}
- {r: 0.74509805, g: 0.22745098, b: 0.15294118, a: 0}
GizmoYOffset: 0
ShowGizmos: 0
CompressionType: 1
m_GizmoYOffset: 0
m_ShowGizmos: 0
m_CompressionType: 1
m_ObservationStacks: 1
--- !u!1 &1729825611722018
GameObject:
m_ObjectHideFlags: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

- component: {fileID: 4688212428263696}
- component: {fileID: 114181230191376748}
m_Layer: 0
m_Name: GridFoodCollectorArea
m_Name: FoodCollectorArea
m_TagString: Untagged
m_Icon: {fileID: 0}
m_NavMeshLayer: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_ClearFlags: 2
m_BackGroundColor: {r: 0.46666667, g: 0.5647059, b: 0.60784316, a: 1}
m_projectionMatrixMode: 1
m_GateFitMode: 2
m_FOVAxisMode: 0
m_GateFitMode: 2
m_FocalLength: 50
m_NormalizedViewPortRect:
serializedVersion: 2

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:

m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 1
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0

245
Project/Assets/ML-Agents/Examples/FoodCollector/Scenes/FoodCollector.unity


m_EnableBakedLightmaps: 1
m_EnableRealtimeLightmaps: 1
m_LightmapEditorSettings:
serializedVersion: 10
serializedVersion: 12
m_Resolution: 2
m_BakeResolution: 40
m_AtlasSize: 1024

m_CompAOExponentDirect: 0
m_ExtractAmbientOcclusion: 0
m_Padding: 2
m_LightmapParameters: {fileID: 15204, guid: 0000000000000000f000000000000000,
type: 0}

m_PVRDirectSampleCount: 32
m_PVRSampleCount: 500
m_PVRBounces: 2
m_PVREnvironmentSampleCount: 500
m_PVREnvironmentReferencePointCount: 2048
m_PVRFilteringMode: 2
m_PVRDenoiserTypeDirect: 0
m_PVRDenoiserTypeIndirect: 0
m_PVRDenoiserTypeAO: 0
m_PVRFilteringMode: 2
m_PVREnvironmentMIS: 0
m_PVRCulling: 1
m_PVRFilteringGaussRadiusDirect: 1
m_PVRFilteringGaussRadiusIndirect: 5

m_PVRFilteringAtrousPositionSigmaAO: 1
m_ShowResolutionOverlay: 1
m_ExportTrainingData: 0
m_TrainingDataDestination: TrainingData
m_LightProbeSampleCountMultiplier: 4
m_LightingDataAsset: {fileID: 112000002, guid: 03723c7f910c3423aa1974f1b9ce8392,
type: 2}
m_UseShadowmask: 1

propertyPath: m_Name
value: GridFoodCollectorArea
objectReference: {fileID: 0}
- target: {fileID: 4137908820211030, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalPosition.x
value: -17.2
objectReference: {fileID: 0}
- target: {fileID: 4259834826122778, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalPosition.x
value: -23.9
objectReference: {fileID: 0}
- target: {fileID: 4419274671784554, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalPosition.x
value: -8.9
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_RootOrder
value: 6
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalPosition.x

value: 0
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalRotation.w
value: 1
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalRotation.x
value: -0
objectReference: {fileID: 0}

value: -0
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalRotation.w
value: 1
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_RootOrder
value: 6
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalEulerAnglesHint.x
value: 0
objectReference: {fileID: 0}

propertyPath: m_LocalEulerAnglesHint.z
value: 0
objectReference: {fileID: 0}
- target: {fileID: 4756368533889646, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalPosition.x
value: -30.4
objectReference: {fileID: 0}
- target: {fileID: 4756368533889646, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalPosition.z
value: -9.9
objectReference: {fileID: 0}
- target: {fileID: 3067525015186813280, guid: b5339e4b990ade14f992aadf3bf8591b,
type: 3}
propertyPath: NumCollidersPerCell
value: 1
objectReference: {fileID: 0}
- target: {fileID: 3067525015186813280, guid: b5339e4b990ade14f992aadf3bf8591b,
type: 3}
propertyPath: EstimatedMaxCollidersPerCell
value: 4
objectReference: {fileID: 0}
- target: {fileID: 5837508007780682603, guid: b5339e4b990ade14f992aadf3bf8591b,
type: 3}
propertyPath: ChannelOffsets.Array.size
value: 1
objectReference: {fileID: 0}
- target: {fileID: 5837508007780682603, guid: b5339e4b990ade14f992aadf3bf8591b,
type: 3}
propertyPath: ShowGizmos
value: 0
objectReference: {fileID: 0}
- target: {fileID: 5837508007780682603, guid: b5339e4b990ade14f992aadf3bf8591b,
type: 3}
propertyPath: ObservationPerCell
value: 6
objectReference: {fileID: 0}
- target: {fileID: 5837508007780682603, guid: b5339e4b990ade14f992aadf3bf8591b,
type: 3}
propertyPath: NumberOfObservations
value: 9600
objectReference: {fileID: 0}
- target: {fileID: 5837508007780682603, guid: b5339e4b990ade14f992aadf3bf8591b,
type: 3}
propertyPath: m_Enabled
value: 1
objectReference: {fileID: 0}
- target: {fileID: 5837508007780682603, guid: b5339e4b990ade14f992aadf3bf8591b,
type: 3}
propertyPath: rootReference
value:
objectReference: {fileID: 190823801}
--- !u!1 &190823801 stripped
GameObject:
m_CorrespondingSourceObject: {fileID: 1706274796045088, guid: b5339e4b990ade14f992aadf3bf8591b,
type: 3}
m_PrefabInstance: {fileID: 190823800}
m_PrefabAsset: {fileID: 0}
--- !u!1001 &392794583
PrefabInstance:
m_ObjectHideFlags: 0

value: 1
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_RootOrder
value: 7
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalPosition.x
value: 0
objectReference: {fileID: 0}

value: 0
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalRotation.w
value: 1
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalRotation.x
value: -0
objectReference: {fileID: 0}

value: -0
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalRotation.w
value: 1
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_RootOrder
value: 7
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalEulerAnglesHint.x
value: 0
objectReference: {fileID: 0}

propertyPath: m_LocalEulerAnglesHint.z
value: 0
objectReference: {fileID: 0}
m_RemovedComponents: []
m_RemovedComponents:
- {fileID: 6035497842152854922, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
- {fileID: 3067525015186813280, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
- {fileID: 8466013622553267624, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
- {fileID: 5837508007780682603, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
- {fileID: 6247312751399400490, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
m_SourcePrefab: {fileID: 100100000, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
--- !u!1 &625137506
GameObject:

m_GameObject: {fileID: 625137506}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 708705254, guid: f70555f144d8491a825f0804e09c671c, type: 3}
m_Script: {fileID: 11500000, guid: 5f7201a12d95ffc409449d95f23cf332, type: 3}
m_Maskable: 1
m_OnCullStateChanged:
m_PersistentCalls:
m_Calls: []

m_TransformParent: {fileID: 0}
m_Modifications:
- target: {fileID: 4943719350691982, guid: 5889392e3f05b448a8a06c5def6c2dec, type: 3}
propertyPath: m_RootOrder
value: 1
objectReference: {fileID: 0}
- target: {fileID: 4943719350691982, guid: 5889392e3f05b448a8a06c5def6c2dec, type: 3}
propertyPath: m_LocalPosition.x
value: 0
objectReference: {fileID: 0}

value: 0
objectReference: {fileID: 0}
- target: {fileID: 4943719350691982, guid: 5889392e3f05b448a8a06c5def6c2dec, type: 3}
propertyPath: m_LocalRotation.w
value: 0.8681629
objectReference: {fileID: 0}
- target: {fileID: 4943719350691982, guid: 5889392e3f05b448a8a06c5def6c2dec, type: 3}
propertyPath: m_LocalRotation.x
value: 0.31598538
objectReference: {fileID: 0}

- target: {fileID: 4943719350691982, guid: 5889392e3f05b448a8a06c5def6c2dec, type: 3}
propertyPath: m_LocalRotation.z
value: 0.13088542
objectReference: {fileID: 0}
- target: {fileID: 4943719350691982, guid: 5889392e3f05b448a8a06c5def6c2dec, type: 3}
propertyPath: m_LocalRotation.w
value: 0.8681629
objectReference: {fileID: 0}
- target: {fileID: 4943719350691982, guid: 5889392e3f05b448a8a06c5def6c2dec, type: 3}
propertyPath: m_RootOrder
value: 1
objectReference: {fileID: 0}
m_RemovedComponents: []
m_SourcePrefab: {fileID: 100100000, guid: 5889392e3f05b448a8a06c5def6c2dec, type: 3}

m_GameObject: {fileID: 965533423}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: -765806418, guid: f70555f144d8491a825f0804e09c671c, type: 3}
m_Script: {fileID: 11500000, guid: fe87c0e1cc204ed48ad3b37840f39efc, type: 3}
m_Maskable: 1
m_OnCullStateChanged:
m_PersistentCalls:
m_Calls: []

m_FillClockwise: 1
m_FillOrigin: 0
m_UseSpriteMesh: 0
m_PixelsPerUnitMultiplier: 1
--- !u!222 &965533426
CanvasRenderer:
m_ObjectHideFlags: 0

m_ClearFlags: 2
m_BackGroundColor: {r: 0.46666667, g: 0.5647059, b: 0.60784316, a: 1}
m_projectionMatrixMode: 1
m_GateFitMode: 2
m_FOVAxisMode: 0
m_GateFitMode: 2
m_FocalLength: 50
m_NormalizedViewPortRect:
serializedVersion: 2

value: 1
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_RootOrder
value: 8
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalPosition.x
value: 0
objectReference: {fileID: 0}

value: 0
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalRotation.w
value: 1
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalRotation.x
value: -0
objectReference: {fileID: 0}

value: -0
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalRotation.w
value: 1
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_RootOrder
value: 8
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalEulerAnglesHint.x
value: 0
objectReference: {fileID: 0}

propertyPath: m_LocalEulerAnglesHint.z
value: 0
objectReference: {fileID: 0}
m_RemovedComponents: []
m_RemovedComponents:
- {fileID: 6035497842152854922, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
- {fileID: 3067525015186813280, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
- {fileID: 8466013622553267624, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
- {fileID: 5837508007780682603, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
- {fileID: 6247312751399400490, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
m_SourcePrefab: {fileID: 100100000, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
--- !u!1 &1064449894
GameObject:

m_GameObject: {fileID: 1064449894}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 1301386320, guid: f70555f144d8491a825f0804e09c671c, type: 3}
m_Script: {fileID: 11500000, guid: dc42784cf147c0c48a680349fa168899, type: 3}
m_Name:
m_EditorClassIdentifier:
m_IgnoreReversedGraphics: 1

m_GameObject: {fileID: 1064449894}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 1980459831, guid: f70555f144d8491a825f0804e09c671c, type: 3}
m_Script: {fileID: 11500000, guid: 0cd44c1031e13a943bb63640046fad76, type: 3}
m_Name:
m_EditorClassIdentifier:
m_UiScaleMode: 1

m_GameObject: {fileID: 1418304524}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 708705254, guid: f70555f144d8491a825f0804e09c671c, type: 3}
m_Script: {fileID: 11500000, guid: 5f7201a12d95ffc409449d95f23cf332, type: 3}
m_Maskable: 1
m_OnCullStateChanged:
m_PersistentCalls:
m_Calls: []

m_GameObject: {fileID: 1956702417}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 1077351063, guid: f70555f144d8491a825f0804e09c671c, type: 3}
m_Script: {fileID: 11500000, guid: 4f231c4fb786f3946a6b90b886c48677, type: 3}
m_Name:
m_EditorClassIdentifier:
m_HorizontalAxis: Horizontal

m_GameObject: {fileID: 1956702417}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: -619905303, guid: f70555f144d8491a825f0804e09c671c, type: 3}
m_Script: {fileID: 11500000, guid: 76c392e42b5098c458856cdf6ecaaaa1, type: 3}
m_Name:
m_EditorClassIdentifier:
m_FirstSelected: {fileID: 0}

value: 1
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_RootOrder
value: 9
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalPosition.x
value: 0
objectReference: {fileID: 0}

value: 0
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalRotation.w
value: 1
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalRotation.x
value: -0
objectReference: {fileID: 0}

value: -0
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalRotation.w
value: 1
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_RootOrder
value: 9
objectReference: {fileID: 0}
- target: {fileID: 4688212428263696, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
propertyPath: m_LocalEulerAnglesHint.x
value: 0
objectReference: {fileID: 0}

propertyPath: m_LocalEulerAnglesHint.z
value: 0
objectReference: {fileID: 0}
m_RemovedComponents: []
m_RemovedComponents:
- {fileID: 6035497842152854922, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
- {fileID: 3067525015186813280, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
- {fileID: 8466013622553267624, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
- {fileID: 5837508007780682603, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
- {fileID: 6247312751399400490, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
m_SourcePrefab: {fileID: 100100000, guid: b5339e4b990ade14f992aadf3bf8591b, type: 3}
--- !u!1001 &2124876351
PrefabInstance:

m_Modifications:
- target: {fileID: 224194346362733190, guid: 3ce107b4a79bc4eef83afde434932a68,
type: 3}
propertyPath: m_LocalPosition.x
propertyPath: m_Pivot.x
propertyPath: m_LocalPosition.y
propertyPath: m_Pivot.y
propertyPath: m_LocalPosition.z
value: 0
propertyPath: m_RootOrder
value: 5
propertyPath: m_LocalRotation.x
propertyPath: m_AnchorMax.x
propertyPath: m_LocalRotation.y
propertyPath: m_AnchorMax.y
propertyPath: m_LocalRotation.z
propertyPath: m_AnchorMin.x
propertyPath: m_LocalRotation.w
value: 1
propertyPath: m_AnchorMin.y
value: 0
propertyPath: m_RootOrder
value: 5
propertyPath: m_SizeDelta.x
value: 0
propertyPath: m_AnchoredPosition.x
propertyPath: m_SizeDelta.y
propertyPath: m_AnchoredPosition.y
propertyPath: m_LocalPosition.x
propertyPath: m_SizeDelta.x
propertyPath: m_LocalPosition.y
propertyPath: m_SizeDelta.y
propertyPath: m_LocalPosition.z
propertyPath: m_AnchorMin.x
value: 0
propertyPath: m_LocalRotation.w
value: 1
propertyPath: m_AnchorMin.y
propertyPath: m_LocalRotation.x
propertyPath: m_AnchorMax.x
propertyPath: m_LocalRotation.y
propertyPath: m_AnchorMax.y
propertyPath: m_LocalRotation.z
propertyPath: m_Pivot.x
propertyPath: m_AnchoredPosition.x
propertyPath: m_Pivot.y
propertyPath: m_AnchoredPosition.y
value: 0
objectReference: {fileID: 0}
m_RemovedComponents: []

693
com.unity.ml-agents.extensions/Runtime/Sensors/GridSensor.cs


using System;
using System.Linq;
using System.Runtime.CompilerServices;
[assembly: InternalsVisibleTo("Unity.ML-Agents.Extensions.EditorTests")]
/// Enum describing what kind of depth type the data should be organized as
/// </summary>
public enum GridDepthType { Channel, ChannelHot, Counting };
/// <summary>
[AddComponentMenu("ML Agents/Grid Sensor", (int)MenuGroup.Sensors)]
public class GridSensor : SensorComponent, ISensor, IBuiltInSensor
public class GridSensor : ISensor, IBuiltInSensor
public string Name;
string Name;
//
// Main Parameters

/// The width of each grid cell.
/// </summary>
[Header("Grid Sensor Settings")]
[Tooltip("The width of each grid cell")]
[Range(0.05f, 1000f)]
public float CellScaleX = 1f;
/// <summary>
/// The depth of each grid cell.
/// The scale of each grid cell.
[Tooltip("The depth of each grid cell")]
[Range(0.05f, 1000f)]
public float CellScaleZ = 1f;
/// <summary>
/// The width of the grid .
/// </summary>
[Tooltip("The width of the grid")]
[Range(2, 2000)]
public int GridNumSideX = 16;
Vector3 CellScale;
/// The depth of the grid .
/// The number of grid on each side.
[Tooltip("The depth of the grid")]
[Range(2, 2000)]
public int GridNumSideZ = 16;
/// <summary>
/// The height of each grid cell. Changes how much of the vertical axis is observed by a cell.
/// </summary>
[Tooltip("The height of each grid cell. Changes how much of the vertical axis is observed by a cell")]
[Range(0.01f, 1000f)]
public float CellScaleY = 0.01f;
Vector3Int GridNumSide;
[Tooltip("Rotate the grid based on the direction the agent is facing")]
public bool RotateToAgent;
bool RotateWithAgent;
[Tooltip("Array holding the depth of each channel")]
public int[] ChannelDepth;
int[] ChannelDepth;
[Tooltip("List of tags that are detected")]
public string[] DetectableObjects;
string[] DetectableObjects;
[Tooltip("The layer mask")]
public LayerMask ObserveMask;
/// <summary>
/// Enum describing what kind of depth type the data should be organized as
/// </summary>
public enum GridDepthType { Channel, ChannelHot };
LayerMask ObserveMask;
[Tooltip("The data layout that the grid should output")]
public GridDepthType gridDepthType = GridDepthType.Channel;
GridDepthType gridDepthType = GridDepthType.Channel;
[Tooltip("The reference of the root of the agent. This is used to disambiguate objects with the same tag as the agent. Defaults to current GameObject")]
public GameObject rootReference;
GameObject rootReference;
int MaxColliderBufferSize;
[Header("Collider Buffer Properties")]
[Tooltip("The absolute max size of the Collider buffer used in the non-allocating Physics calls. In other words" +
" the Collider buffer will never grow beyond this number even if there are more Colliders in the Grid Cell.")]
public int MaxColliderBufferSize = 500;
[Tooltip(
"The Estimated Max Number of Colliders to expect per cell. This number is used to " +
"pre-allocate an array of Colliders in order to take advantage of the OverlapBoxNonAlloc " +
"Physics API. If the number of colliders found is >= InitialColliderBufferSize the array " +
"will be resized to double its current size. The hard coded absolute size is 500.")]
public int InitialColliderBufferSize = 4;
int InitialColliderBufferSize;
Collider[] m_ColliderBuffer;
float[] m_ChannelBuffer;

/// <summary>
/// The total number of observations per cell of the grid. Its equivalent to the "channel" on the outgoing tensor.
/// </summary>
[HideInInspector]
public int ObservationPerCell;
/// <summary>
/// The total number of observations that this GridSensor provides. It is the length of m_PerceptionBuffer.
/// </summary>
[HideInInspector]
public int NumberOfObservations;
int ObservationPerCell;
[HideInInspector]
public int[] ChannelOffsets;
int[] ChannelOffsets;
protected float[] m_PerceptionBuffer;
internal float[] m_PerceptionBuffer;
protected float[] m_ChannelHotDefaultPerceptionBuffer;
float[] m_ChannelHotDefaultPerceptionBuffer;
protected Color[] m_PerceptionColors;
Color[] m_PerceptionColors;
protected Texture2D m_perceptionTexture2D;
Texture2D m_perceptionTexture2D;
//
// Utility Constants Calculated on Init

/// Number of PNG formated images that are sent to python during training.
/// </summary>
private int NumImages;
/// <summary>
/// Number of relevant channels on the last image that is sent/
/// </summary>
private int NumChannelsOnLastImage;
/// <summary>
protected float InverseSphereRadius;
float InverseSphereRadius;
private int NumCells;
/// <summary>
/// Difference between GridNumSideZ and gridNumSideX.
/// </summary>
protected int DiffNumSideZX = 0;
int NumCells;
protected float OffsetGridNumSide = 7.5f; // (gridNumSideZ - 1) / 2;
/// <summary>
/// Half of the grid in the X direction
/// </summary>
private float HalfOfGridX;
/// <summary>
/// Half of the grid in the z direction
/// </summary>
private float HalfOfGridZ;
/// <summary>
/// Used in the PointToCell method to scale the x value to land in the calculated cell.
/// </summary>
private float PointToCellScalingX;
/// <summary>
/// Used in the PointToCell method to scale the y value to land in the calculated cell.
/// </summary>
private float PointToCellScalingZ;
/// <summary>
/// Bool if initialized or not.
/// </summary>
protected bool Initialized = false;
float OffsetGridNumSide = 7.5f; // (gridNumSideZ - 1) / 2;
private ObservationSpec m_ObservationSpec;
ObservationSpec m_ObservationSpec;
/// <summary>
/// Array of Colors used for the grid gizmos.
/// </summary>
[Header("Debug Options")]
[Tooltip("Array of Colors used for the grid gizmos")]
public Color[] DebugColors;
SensorCompressionType m_CompressionType = SensorCompressionType.PNG;
/// The height of the gizmos grid.
/// Array of colors displaying the DebugColors for each cell in OnDrawGizmos. Only updated if ShowGizmos.
[Tooltip("The height of the gizmos grid")]
public float GizmoYOffset = 0f;
int[] m_CellActivity;
/// Whether to show gizmos or not.
/// Array of global positions where each position is the center of a cell.
[Tooltip("Whether to show gizmos or not")]
public bool ShowGizmos = false;
public SensorCompressionType CompressionType = SensorCompressionType.PNG;
Vector3[] m_GizmoCellPosition;
/// Array of colors displaying the DebugColors for each cell in OnDrawGizmos. Only updated if ShowGizmos.
/// Array of local positions where each position is the center of a cell.
protected Color[] CellActivity;
Vector3[] CellPoints;
/// <summary>
/// Array of positions where each position is the center of a cell.
/// </summary>
private Vector3[] CellPoints;
public GridSensor(
string name,
Vector3 cellScale,
Vector3Int gridNumSide,
bool rotateWithAgent,
int[] channelDepth,
string[] detectableObjects,
LayerMask observeMask,
GridDepthType depthType,
GameObject root,
SensorCompressionType compression,
int maxColliderBufferSize,
int initialColliderBufferSize
)
{
Name = name;
CellScale = cellScale;
GridNumSide = gridNumSide;
if (GridNumSide.y != 1)
{
throw new UnityAgentsException("GridSensor only supports 2D grids.");
}
RotateWithAgent = rotateWithAgent;
ChannelDepth = channelDepth;
DetectableObjects = detectableObjects;
ObserveMask = observeMask;
gridDepthType = depthType;
rootReference = root;
CompressionType = compression;
MaxColliderBufferSize = maxColliderBufferSize;
InitialColliderBufferSize = initialColliderBufferSize;
/// <summary>
/// List representing the multiple compressed images of all of the grids
/// </summary>
private List<byte[]> compressedImgs;
if (gridDepthType == GridDepthType.Counting && DetectableObjects.Length != ChannelDepth.Length)
{
throw new UnityAgentsException("The channels of a CountingGridSensor is equal to the number of detectableObjects");
}
/// <summary>
/// List representing the sizes of the multiple images so they can be properly reconstructed on the python side
/// </summary>
private List<byte[]> byteSizesBytesList;
InitGridParameters();
InitDepthType();
InitCellPoints();
ResetPerceptionBuffer();
private Color DebugDefaultColor = new Color(1f, 1f, 1f, 0.25f);
m_ObservationSpec = ObservationSpec.Visual(GridNumSide.x, GridNumSide.z, ObservationPerCell);
m_perceptionTexture2D = new Texture2D(GridNumSide.x, GridNumSide.z, TextureFormat.RGB24, false);
m_ColliderBuffer = new Collider[Math.Min(MaxColliderBufferSize, InitialColliderBufferSize)];
}
/// <inheritdoc/>
public override ISensor[] CreateSensors()
public SensorCompressionType CompressionType
return new ISensor[] { this };
get { return m_CompressionType; }
set { m_CompressionType = value; }
/// <summary>
/// Sets the parameters of the grid sensor
/// </summary>
/// <param name="detectableObjects">array of strings representing the tags to be detected by the sensor</param>
/// <param name="channelDepth">array of ints representing the depth of each channel</param>
/// <param name="gridDepthType">enum representing the GridDepthType of the sensor</param>
/// <param name="cellScaleX">float representing the X scaling of each cell</param>
/// <param name="cellScaleZ">float representing the Z scaling of each cell</param>
/// <param name="gridWidth">int representing the number of cells in the X direction. Width of the Grid</param>
/// <param name="gridHeight">int representing the number of cells in the Z direction. Height of the Grid</param>
/// <param name="observeMaskInt">int representing the layer mask to observe</param>
/// <param name="rotateToAgent">bool if true then the grid is rotated to the rotation of the transform the rootReference</param>
/// <param name="debugColors">array of colors corresponding the the tags in the detectableObjects array</param>
public virtual void SetParameters(string[] detectableObjects, int[] channelDepth, GridDepthType gridDepthType,
float cellScaleX, float cellScaleZ, int gridWidth, int gridHeight, int observeMaskInt, bool rotateToAgent, Color[] debugColors)
public int[] CellActivity
this.ObserveMask = observeMaskInt;
this.DetectableObjects = detectableObjects;
this.ChannelDepth = channelDepth;
this.gridDepthType = gridDepthType;
this.CellScaleX = cellScaleX;
this.CellScaleZ = cellScaleZ;
this.GridNumSideX = gridWidth;
this.GridNumSideZ = gridHeight;
this.RotateToAgent = rotateToAgent;
this.DiffNumSideZX = (GridNumSideZ - GridNumSideX);
this.OffsetGridNumSide = (GridNumSideZ - 1f) / 2f;
this.DebugColors = debugColors;
get { return m_CellActivity; }
public void InitGridParameters()
void InitGridParameters()
NumCells = GridNumSideX * GridNumSideZ;
float sphereRadiusX = (CellScaleX * GridNumSideX) / Mathf.Sqrt(2);
float sphereRadiusZ = (CellScaleZ * GridNumSideZ) / Mathf.Sqrt(2);
NumCells = GridNumSide.x * GridNumSide.z;
float sphereRadiusX = (CellScale.x * GridNumSide.x) / Mathf.Sqrt(2);
float sphereRadiusZ = (CellScale.z * GridNumSide.z) / Mathf.Sqrt(2);
ChannelOffsets = new int[ChannelDepth.Length];
DiffNumSideZX = (GridNumSideZ - GridNumSideX);
OffsetGridNumSide = (GridNumSideZ - 1f) / 2f;
HalfOfGridX = CellScaleX * GridNumSideX / 2;
HalfOfGridZ = CellScaleZ * GridNumSideZ / 2;
PointToCellScalingX = GridNumSideX / (CellScaleX * GridNumSideX);
PointToCellScalingZ = GridNumSideZ / (CellScaleZ * GridNumSideZ);
OffsetGridNumSide = (GridNumSide.z - 1f) / 2f;
}
/// <summary>

public virtual void InitDepthType()
void InitDepthType()
switch (gridDepthType)
if (gridDepthType == GridDepthType.ChannelHot)
case GridDepthType.Channel:
ObservationPerCell = ChannelDepth.Length;
break;
ObservationPerCell = ChannelDepth.Sum();
case GridDepthType.ChannelHot:
ObservationPerCell = 0;
ChannelOffsets[ChannelOffsets.Length - 1] = 0;
for (int i = 1; i < ChannelDepth.Length; i++)
{
ChannelOffsets[i] = ChannelOffsets[i - 1] + ChannelDepth[i - 1];
}
ChannelOffsets = new int[ChannelDepth.Length];
for (int i = 1; i < ChannelDepth.Length; i++)
{
ChannelOffsets[i] = ChannelOffsets[i - 1] + ChannelDepth[i - 1];
}
for (int i = 0; i < ChannelDepth.Length; i++)
m_ChannelHotDefaultPerceptionBuffer = new float[ObservationPerCell];
for (int i = 0; i < ChannelDepth.Length; i++)
{
if (ChannelDepth[i] > 1)
ObservationPerCell += ChannelDepth[i];
m_ChannelHotDefaultPerceptionBuffer[ChannelOffsets[i]] = 1;
break;
}
}
else
{
ObservationPerCell = ChannelDepth.Length;
}
// The maximum number of channels in the final output must be less than 255 * 3 because the "number of PNG images" to generate must fit in one byte

/// <summary>
/// Initializes the location of the CellPoints property
/// </summary>
private void InitCellPoints()
void InitCellPoints()
CellPoints[i] = CellToPoint(i, false);
CellPoints[i] = CellToLocalPosition(i);
/// <summary>
/// Initializes the m_ChannelHotDefaultPerceptionBuffer with default data in the case that the grid depth type is ChannelHot
/// </summary>
public virtual void InitChannelHotDefaultPerceptionBuffer()
{
m_ChannelHotDefaultPerceptionBuffer = new float[ObservationPerCell];
for (int i = 0; i < ChannelDepth.Length; i++)
{
if (ChannelDepth[i] > 1)
{
m_ChannelHotDefaultPerceptionBuffer[ChannelOffsets[i]] = 1;
}
}
}
/// <summary>
/// Initializes the m_PerceptionBuffer as the main data storage property
/// Calculates the NumImages and NumChannelsOnLastImage that are used for serializing m_PerceptionBuffer
/// </summary>
public void InitPerceptionBuffer()
{
if (Application.isPlaying)
Initialized = true;
NumberOfObservations = ObservationPerCell * NumCells;
m_PerceptionBuffer = new float[NumberOfObservations];
if (gridDepthType == GridDepthType.ChannelHot)
{
InitChannelHotDefaultPerceptionBuffer();
}
m_PerceptionColors = new Color[NumCells];
NumImages = ObservationPerCell / 3;
NumChannelsOnLastImage = ObservationPerCell % 3;
if (NumChannelsOnLastImage == 0)
NumChannelsOnLastImage = 3;
else
NumImages += 1;
CellActivity = new Color[NumCells];
}
/// <summary>
/// Calls the initialization methods. Creates the data storing properties used to send the data
/// Establishes
/// </summary>
public virtual void Start()
{
InitGridParameters();
InitDepthType();
InitCellPoints();
InitPerceptionBuffer();
m_ColliderBuffer = new Collider[Math.Min(MaxColliderBufferSize, InitialColliderBufferSize)];
// Default root reference to current game object
if (rootReference == null)
rootReference = gameObject;
m_ObservationSpec = ObservationSpec.Visual(GridNumSideX, GridNumSideZ, ObservationPerCell);
compressedImgs = new List<byte[]>();
byteSizesBytesList = new List<byte[]>();
m_perceptionTexture2D = new Texture2D(GridNumSideX, GridNumSideZ, TextureFormat.RGB24, false);
}
/// <inheritdoc cref="ISensor.Reset"/>
void ISensor.Reset() { }
/// <inheritdoc/>
public void Reset() { }
public void ClearPerceptionBuffer()
public void ResetPerceptionBuffer()
{
if (m_PerceptionBuffer != null)
{

}
else
{
m_PerceptionBuffer = new float[NumberOfObservations];
m_PerceptionBuffer = new float[ObservationPerCell * NumCells];
m_ChannelBuffer = new float[ChannelDepth.Length];
m_PerceptionColors = new Color[NumCells];
m_GizmoCellPosition = new Vector3[NumCells];
}
if (ShowGizmos)
{
// Ensure to init arrays if not yet assigned (for editor)
if (CellActivity == null)
CellActivity = new Color[NumCells];
public void ResetGizmoBuffer()
{
// Ensure to init arrays if not yet assigned (for editor)
if (m_CellActivity == null)
m_CellActivity = new int[NumCells];
// Assign the default color to the cell activities
for (int i = 0; i < NumCells; i++)
{
CellActivity[i] = DebugDefaultColor;
}
// Assign the default color to the cell activities
for (int i = 0; i < NumCells; i++)
{
m_CellActivity[i] = -1;
/// <inheritdoc/>
public string GetName()

/// <inheritdoc/>
public virtual CompressionSpec GetCompressionSpec()
public CompressionSpec GetCompressionSpec()
{
return new CompressionSpec(CompressionType);
}

{
using (TimerStack.Instance.Scoped("GridSensor.GetCompressedObservation"))
{
Perceive(); // Fill the perception buffer with observed data
for (int i = 0; i < NumImages - 1; i++)
var numImages = (ObservationPerCell + 2) / 3;
for (int i = 0; i < numImages; i++)
ChannelsToTexture(3 * i, 3);
var channelIndex = 3 * i;
ChannelsToTexture(channelIndex, Math.Min(3, ObservationPerCell - channelIndex));
ChannelsToTexture(3 * (NumImages - 1), NumChannelsOnLastImage);
allBytes.AddRange(m_perceptionTexture2D.EncodeToPNG());
return allBytes.ToArray();
}
}

/// </summary>
/// <param name="channelIndex"></param>
/// <param name="numChannelsToAdd"></param>
protected void ChannelsToTexture(int channelIndex, int numChannelsToAdd)
void ChannelsToTexture(int channelIndex, int numChannelsToAdd)
{
for (int i = 0; i < NumCells; i++)
{

/// <summary>
/// Perceive - Clears the buffers, calls overlap box on the actual cell (the actual perception part)
/// for all found colliders, LoadObjectData is called
/// at the end, Perceive returns the float array of the perceptions
/// <returns>A float[] containing all of the information collected from the gridsensor</returns>
public float[] Perceive()
internal void Perceive()
return Array.Empty<float>();
return;
ClearPerceptionBuffer();
ResetPerceptionBuffer();
var halfCellScale = new Vector3(CellScaleX / 2f, CellScaleY, CellScaleZ / 2f);
var halfCellScale = new Vector3(CellScale.x / 2f, CellScale.y, CellScale.z / 2f);
int numFound;
Vector3 cellCenter;
if (RotateToAgent)
{
Transform transform1;
cellCenter = (transform1 = transform).TransformPoint(CellPoints[cellIndex]);
numFound = BufferResizingOverlapBoxNonAlloc(cellCenter, halfCellScale, transform1.rotation);
}
else
{
cellCenter = transform.position + CellPoints[cellIndex];
numFound = BufferResizingOverlapBoxNonAlloc(cellCenter, halfCellScale, Quaternion.identity);
}
var cellCenter = GetCellGlobalPosition(cellIndex);
var numFound = BufferResizingOverlapBoxNonAlloc(cellCenter, halfCellScale, GetGridRotation());
ParseColliders(m_ColliderBuffer, numFound, cellIndex, cellCenter);
if (gridDepthType == GridDepthType.Counting)
{
ParseCollidersAll(m_ColliderBuffer, numFound, cellIndex, cellCenter);
}
else
{
ParseCollidersClosest(m_ColliderBuffer, numFound, cellIndex, cellCenter);
}
return m_PerceptionBuffer;
}
/// <summary>

/// <param name="numFound">Number of colliders found.</param>
/// <param name="cellIndex">The index of the cell</param>
/// <param name="cellCenter">The center position of the cell</param>
protected virtual void ParseColliders(Collider[] foundColliders, int numFound, int cellIndex, Vector3 cellCenter)
void ParseCollidersClosest(Collider[] foundColliders, int numFound, int cellIndex, Vector3 cellCenter)
{
Profiler.BeginSample("GridSensor.ParseColliders");
GameObject closestColliderGo = null;

}
if (!ReferenceEquals(closestColliderGo, null))
{
}
Profiler.EndSample();
}
/// <summary>
/// For each collider, calls LoadObjectData on the gameobejct
/// </summary>
/// <param name="foundColliders">The array of colliders</param>
/// <param name="cellIndex">The cell index the collider is in</param>
/// <param name="cellCenter">the center of the cell the collider is in</param>
void ParseCollidersAll(Collider[] foundColliders, int numFound, int cellIndex, Vector3 cellCenter)
{
Profiler.BeginSample("GridSensor.ParseColliders");
GameObject currentColliderGo = null;
Vector3 closestColliderPoint = Vector3.zero;
for (int i = 0; i < numFound; i++)
{
currentColliderGo = foundColliders[i].gameObject;
// Continue if the current collider go is the root reference
if (currentColliderGo == rootReference)
continue;
closestColliderPoint = foundColliders[i].ClosestPointOnBounds(cellCenter);
LoadObjectData(currentColliderGo, cellIndex,
Vector3.Distance(closestColliderPoint, rootReference.transform.position) * InverseSphereRadius);
}
Profiler.EndSample();
}

/// </example>
protected virtual float[] GetObjectData(GameObject currentColliderGo, float typeIndex, float normalizedDistance)
{
if (m_ChannelBuffer == null)
{
m_ChannelBuffer = new float[ChannelDepth.Length];
}
Array.Clear(m_ChannelBuffer, 0, m_ChannelBuffer.Length);
m_ChannelBuffer[0] = typeIndex;
return m_ChannelBuffer;

var channelHotVals = new ArraySegment<float>(m_PerceptionBuffer, cellIndex * ObservationPerCell, ObservationPerCell);
for (var i = 0; i < DetectableObjects.Length; i++)
{
for (var ii = 0; ii < channelHotVals.Count; ii++)
if (gridDepthType != GridDepthType.Counting)
m_PerceptionBuffer[channelHotVals.Offset + ii] = 0f;
for (var ii = 0; ii < channelHotVals.Count; ii++)
{
m_PerceptionBuffer[channelHotVals.Offset + ii] = 0f;
}
}
if (!ReferenceEquals(currentColliderGo, null) && currentColliderGo.CompareTag(DetectableObjects[i]))

float[] channelValues = GetObjectData(currentColliderGo, (float)i + 1, normalizedDistance);
var channelValues = GetObjectData(currentColliderGo, (float)i + 1, normalizedDistance);
if (ShowGizmos)
{
Color debugRayColor = Color.white;
if (DebugColors.Length > 0)
{
debugRayColor = DebugColors[i];
}
CellActivity[cellIndex] = new Color(debugRayColor.r, debugRayColor.g, debugRayColor.b, .5f);
}
switch (gridDepthType)
{

}
break;
}
case GridDepthType.Counting:
{
// The observations are "channel count" so each grid is WxHxC where C is the number of tags
// This means that each value channelValues[i] is a counter of gameobject included into grid cells
// where i is the index of the tag in DetectableObjects
int countIndex = cellIndex * ObservationPerCell + i;
m_PerceptionBuffer[countIndex] = Mathf.Min(1f, m_PerceptionBuffer[countIndex] + 1f / ChannelDepth[i]);
break;
}
}
break;

}
/// <summary>Converts the index of the cell to the 3D point (y is zero)</summary>
/// <returns>Vector3 of the position of the center of the cell</returns>
/// <summary>Converts the index of the cell to the 3D point (y is zero) relative to grid center</summary>
/// <returns>Vector3 of the position of the center of the cell relative to grid center</returns>
/// <param name="shouldTransformPoint">Bool weather to transform the point to the current transform</param>
protected Vector3 CellToPoint(int cell, bool shouldTransformPoint = true)
Vector3 CellToLocalPosition(int cellIndex)
float x = (cell % GridNumSideZ - OffsetGridNumSide) * CellScaleX;
float z = (cell / GridNumSideZ - OffsetGridNumSide) * CellScaleZ - DiffNumSideZX;
if (shouldTransformPoint)
return transform.TransformPoint(new Vector3(x, 0, z));
float x = (cellIndex % GridNumSide.z - OffsetGridNumSide) * CellScale.x;
float z = (cellIndex / GridNumSide.z - OffsetGridNumSide) * CellScale.z - (GridNumSide.z - GridNumSide.x);
/// <summary>Finds the cell in which the given global point falls</summary>
/// <returns>
/// The index of the cell in which the global point falls or -1 if the point does not fall into a cell
/// </returns>
/// <param name="globalPoint">The 3D point in global space</param>
public int PointToCell(Vector3 globalPoint)
internal Vector3 GetCellGlobalPosition(int cellIndex)
Vector3 point = transform.InverseTransformPoint(globalPoint);
if (point.x < -HalfOfGridX || point.x > HalfOfGridX || point.z < -HalfOfGridZ || point.z > HalfOfGridZ)
return -1;
float x = point.x + HalfOfGridX;
float z = point.z + HalfOfGridZ;
int _x = (int)Mathf.Floor(x * PointToCellScalingX);
int _z = (int)Mathf.Floor(z * PointToCellScalingZ);
return GridNumSideX * _z + _x;
if (RotateWithAgent)
{
return rootReference.transform.TransformPoint(CellPoints[cellIndex]);
}
else
{
return CellPoints[cellIndex] + rootReference.transform.position;
}
/// <summary>Copies the data from one cell to another</summary>
/// <param name="fromCellID">index of the cell to copy from</param>
/// <param name="toCellID">index of the cell to copy into</param>
protected void CopyCellData(int fromCellID, int toCellID)
internal Quaternion GetGridRotation()
Array.Copy(m_PerceptionBuffer,
fromCellID * ObservationPerCell,
m_PerceptionBuffer,
toCellID * ObservationPerCell,
ObservationPerCell);
if (ShowGizmos)
CellActivity[toCellID] = CellActivity[fromCellID];
}
void OnDrawGizmos()
{
if (ShowGizmos)
{
if (Application.isEditor && !Application.isPlaying)
Start();
Perceive();
var scale = new Vector3(CellScaleX, 1, CellScaleZ);
var offset = new Vector3(0, GizmoYOffset, 0);
var oldGizmoMatrix = Gizmos.matrix;
for (var i = 0; i < NumCells; i++)
{
Matrix4x4 cubeTransform;
if (RotateToAgent)
{
cubeTransform = Matrix4x4.TRS(CellToPoint(i) + offset, transform.rotation, scale);
}
else
{
cubeTransform = Matrix4x4.TRS(CellToPoint(i, false) + transform.position + offset, Quaternion.identity, scale);
}
Gizmos.matrix = oldGizmoMatrix * cubeTransform;
Gizmos.color = CellActivity[i];
Gizmos.DrawCube(Vector3.zero, Vector3.one);
}
Gizmos.matrix = oldGizmoMatrix;
if (Application.isEditor && !Application.isPlaying)
DestroyImmediate(m_perceptionTexture2D);
}
return RotateWithAgent ? rootReference.transform.rotation : Quaternion.identity;
void ISensor.Update()
public void Update()
{
using (TimerStack.Instance.Scoped("GridSensor.Update"))
{

/// <summary>Gets the observation shape</summary>
/// <returns>int[] of the observation shape</returns>
/// <inheritdoc/>
// Lazy update
var shape = m_ObservationSpec.Shape;
if (shape[0] != GridNumSideX || shape[1] != GridNumSideZ || shape[2] != ObservationPerCell)
{
m_ObservationSpec = ObservationSpec.Visual(GridNumSideX, GridNumSideZ, ObservationPerCell);
}
return m_ObservationSpec;
}

using (TimerStack.Instance.Scoped("GridSensor.WriteToTensor"))
using (TimerStack.Instance.Scoped("GridSensor.Write"))
for (var h = GridNumSideZ - 1; h >= 0; h--) // height
for (var h = GridNumSide.z - 1; h >= 0; h--)
for (var w = 0; w < GridNumSideX; w++) // width
for (var w = 0; w < GridNumSide.x; w++)
for (var d = 0; d < ObservationPerCell; d++) // depth
for (var d = 0; d < ObservationPerCell; d++)
{
writer[h, w, d] = m_PerceptionBuffer[index];
index++;

return index;
}
}
internal int[] PerceiveGizmoColor()
{
ResetGizmoBuffer();
var halfCellScale = new Vector3(CellScale.x / 2f, CellScale.y, CellScale.z / 2f);
for (var cellIndex = 0; cellIndex < NumCells; cellIndex++)
{
var cellCenter = GetCellGlobalPosition(cellIndex);
var numFound = BufferResizingOverlapBoxNonAlloc(cellCenter, halfCellScale, GetGridRotation());
var minDistanceSquared = float.MaxValue;
var tagIndex = -1;
for (var i = 0; i < numFound; i++)
{
var currentColliderGo = m_ColliderBuffer[i].gameObject;
if (ReferenceEquals(currentColliderGo, rootReference))
continue;
var closestColliderPoint = m_ColliderBuffer[i].ClosestPointOnBounds(cellCenter);
var currentDistanceSquared = (closestColliderPoint - rootReference.transform.position).sqrMagnitude;
// Checks if our colliders contain a detectable object
var index = -1;
for (var ii = 0; ii < DetectableObjects.Length; ii++)
{
if (currentColliderGo.CompareTag(DetectableObjects[ii]))
{
index = ii;
break;
}
}
if (index > -1 && currentDistanceSquared < minDistanceSquared)
{
minDistanceSquared = currentDistanceSquared;
tagIndex = index;
}
}
CellActivity[cellIndex] = tagIndex;
}
return CellActivity;
}
internal Vector3[] GetGizmoPositions()
{
for (var i = 0; i < NumCells; i++)
{
m_GizmoCellPosition[i] = GetCellGlobalPosition(i);
}
return m_GizmoCellPosition;
}
}
}

2
com.unity.ml-agents.extensions/Runtime/Sensors/GridSensorComponent.cs.meta


fileFormatVersion: 2
guid: bf4578dd22673114ebe87bd08bd84c94
guid: 2a501962d056745d1a30e99146ee39fe
MonoImporter:
externalObjects: {}
serializedVersion: 2

128
com.unity.ml-agents.extensions/Tests/Editor/Sensors/ChannelHotPerceiveTests.cs


{
GameObject testGo;
GameObject boxGo;
SimpleTestGridSensor gridSensor;
SimpleTestGridSensorComponent gridSensorComponent;
GridSensorDummyData dummyData;
// Use built-in tags

{
testGo = new GameObject("test");
testGo.transform.position = Vector3.zero;
gridSensor = testGo.AddComponent<SimpleTestGridSensor>();
gridSensorComponent = testGo.AddComponent<SimpleTestGridSensorComponent>();
boxGo = new GameObject("block");
boxGo.tag = k_Tag1;

int[] depths = { 1 };
dummyData.Data = new[] { -0.1f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
yield return null;

int[] depths = { 1 };
dummyData.Data = new[] { 1.1f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
yield return null;

int[] depths = { 1 };
dummyData.Data = new[] { .2f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 1, output.Length);
Assert.AreEqual(10 * 10 * 1, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

int[] depths = { 3 };
dummyData.Data = new[] { -1f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
yield return null;

int[] depths = { 3 };
dummyData.Data = new[] { 4f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
yield return null;

int[] depths = { 3 };
dummyData.Data = new[] { 2f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 3, output.Length);
Assert.AreEqual(10 * 10 * 3, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

int[] depths = { 3 };
dummyData.Data = new[] { 2.4f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 3, output.Length);
Assert.AreEqual(10 * 10 * 3, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

int[] depths = { 1, 1 };
dummyData.Data = new float[] { -1, 1 };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
yield return null;

int[] depths = { 1, 1 };
dummyData.Data = new float[] { 1, 3 };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
yield return null;

int[] depths = { 1, 1 };
dummyData.Data = new[] { .4f, .3f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 2, output.Length);
Assert.AreEqual(10 * 10 * 2, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

int[] depths = { 1, 3 };
dummyData.Data = new[] { .4f, 4f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
yield return null;

int[] depths = { 1, 3 };
dummyData.Data = new[] { .4f, 1f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 4, output.Length);
Assert.AreEqual(10 * 10 * 4, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

int[] depths = { 3, 1 };
dummyData.Data = new[] { 1f, .4f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 4, output.Length);
Assert.AreEqual(10 * 10 * 4, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

int[] depths = { 3, 3 };
dummyData.Data = new[] { 1f, 2.2f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 6, output.Length);
Assert.AreEqual(10 * 10 * 6, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

int[] depths = { 5, 1, 3 };
dummyData.Data = new[] { 3f, .6f, 2.2f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 9, output.Length);
Assert.AreEqual(10 * 10 * 9, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

int[] depths = { 5, 1, 3 };
dummyData.Data = new[] { 3f, .6f, 2.2f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 9, output.Length);
Assert.AreEqual(10 * 10 * 9, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 9, output.Length);
Assert.AreEqual(10 * 10 * 9, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
}
}

20
com.unity.ml-agents.extensions/Tests/Editor/Sensors/ChannelHotShapeTests.cs


{
GameObject testGo;
GridSensor gridSensor;
GridSensorComponent gridSensorComponent;
[SetUp]
public void SetupScene()

gridSensor = testGo.AddComponent<GridSensor>();
gridSensorComponent = testGo.AddComponent<GridSensorComponent>();
}
[TearDown]

string[] tags = { "Box", "Ball" };
int[] depths = { 1 };
Color[] colors = { Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
var expectedShape = new InplaceArray<int>(10, 10, 1);
Assert.AreEqual(expectedShape, gridSensor.GetObservationSpec().Shape);

string[] tags = { "Box", "Ball" };
int[] depths = { 2 };
Color[] colors = { Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
var expectedShape = new InplaceArray<int>(10, 10, 2);
Assert.AreEqual(expectedShape, gridSensor.GetObservationSpec().Shape);

string[] tags = { "Box", "Ball" };
int[] depths = { 2, 1 };
Color[] colors = { Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
var expectedShape = new InplaceArray<int>(10, 10, 3);
Assert.AreEqual(expectedShape, gridSensor.GetObservationSpec().Shape);

string[] tags = { "Box", "Ball" };
int[] depths = { 3, 3 };
Color[] colors = { Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
var expectedShape = new InplaceArray<int>(10, 10, 6);
Assert.AreEqual(expectedShape, gridSensor.GetObservationSpec().Shape);

128
com.unity.ml-agents.extensions/Tests/Editor/Sensors/ChannelPerceiveTests.cs


{
GameObject testGo;
GameObject boxGo;
SimpleTestGridSensor gridSensor;
SimpleTestGridSensorComponent gridSensorComponent;
GridSensorDummyData dummyData;
// Use built-in tags

{
testGo = new GameObject("test");
testGo.transform.position = Vector3.zero;
gridSensor = testGo.AddComponent<SimpleTestGridSensor>();
gridSensorComponent = testGo.AddComponent<SimpleTestGridSensorComponent>();
boxGo = new GameObject("block");
boxGo.tag = k_Tag1;

int[] depths = { 1 };
dummyData.Data = new[] { -0.1f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
yield return null;

int[] depths = { 1 };
dummyData.Data = new[] { 1.1f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
yield return null;

int[] depths = { 1 };
dummyData.Data = new[] { .2f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 1, output.Length);
Assert.AreEqual(10 * 10 * 1, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

int[] depths = { 3 };
dummyData.Data = new[] { -1f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
yield return null;

int[] depths = { 3 };
dummyData.Data = new[] { 4f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
yield return null;

int[] depths = { 3 };
dummyData.Data = new[] { 2f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 1, output.Length);
Assert.AreEqual(10 * 10 * 1, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

int[] depths = { 3 };
dummyData.Data = new[] { 2.4f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 1, output.Length);
Assert.AreEqual(10 * 10 * 1, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

int[] depths = { 1, 1 };
dummyData.Data = new float[] { -1, 1 };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
yield return null;

int[] depths = { 1, 1 };
dummyData.Data = new float[] { 1, 3 };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
yield return null;

int[] depths = { 1, 1 };
dummyData.Data = new[] { .4f, .3f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 2, output.Length);
Assert.AreEqual(10 * 10 * 2, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

int[] depths = { 1, 3 };
dummyData.Data = new[] { .4f, 4f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
yield return null;

int[] depths = { 1, 3 };
dummyData.Data = new[] { .4f, 1f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 2, output.Length);
Assert.AreEqual(10 * 10 * 2, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

int[] depths = { 3, 1 };
dummyData.Data = new[] { 1f, .4f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 2, output.Length);
Assert.AreEqual(10 * 10 * 2, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

int[] depths = { 3, 3 };
dummyData.Data = new[] { 1f, 2.2f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 2, output.Length);
Assert.AreEqual(10 * 10 * 2, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

int[] depths = { 5, 1, 3 };
dummyData.Data = new[] { 3f, .6f, 2.2f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 3, output.Length);
Assert.AreEqual(10 * 10 * 3, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

int[] depths = { 5, 1, 3 };
dummyData.Data = new[] { 3f, .6f, 2.2f };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 3, output.Length);
Assert.AreEqual(10 * 10 * 3, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 3, output.Length);
Assert.AreEqual(10 * 10 * 3, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
}
}

16
com.unity.ml-agents.extensions/Tests/Editor/Sensors/ChannelShapeTests.cs


{
GameObject testGo;
GridSensor gridSensor;
GridSensorComponent gridSensorComponent;
[SetUp]
public void SetupScene()

gridSensor = testGo.AddComponent<GridSensor>();
gridSensorComponent = testGo.AddComponent<GridSensorComponent>();
}
[TearDown]

string[] tags = { "Box" };
int[] depths = { 1 };
Color[] colors = { Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
var expectedShape = new InplaceArray<int>(10, 10, 1);
Assert.AreEqual(expectedShape, gridSensor.GetObservationSpec().Shape);

string[] tags = { "Box", "Ball" };
int[] depths = { 1, 1 };
Color[] colors = { Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
var expectedShape = new InplaceArray<int>(10, 10, 2);
Assert.AreEqual(expectedShape, gridSensor.GetObservationSpec().Shape);

string[] tags = { "Box", "Ball" };
int[] depths = { 1, 1, 1, 1, 1, 1, 1 };
Color[] colors = { Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
var expectedShape = new InplaceArray<int>(10, 10, 7);
Assert.AreEqual(expectedShape, gridSensor.GetObservationSpec().Shape);

45
com.unity.ml-agents.extensions/Tests/Editor/Sensors/CountingGridSensorPerceiveTests.cs


GameObject boxGo;
GameObject boxGoTwo;
GameObject boxGoThree;
CountingGridSensor gridSensor;
// CountingGridSensor gridSensor;
GridSensorComponent gridSensorComponent;
// Use built-in tags
const string k_Tag1 = "Player";

{
testGo = new GameObject("test");
testGo.transform.position = Vector3.zero;
gridSensor = testGo.AddComponent<CountingGridSensor>();
gridSensorComponent = testGo.AddComponent<GridSensorComponent>();
boxGo = CreateBlock(new Vector3(3f, 0f, 3f), k_Tag1, "box1");

string[] tags = { k_Tag1 };
int[] depths = { 1 };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Counting,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 1, output.Length);
Assert.AreEqual(10 * 10 * 1, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

int[] depths = { 1 };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Counting,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 1, output.Length);
Assert.AreEqual(10 * 10 * 1, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

int[] depths = { 4 };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Counting,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 1, output.Length);
Assert.AreEqual(10 * 10 * 1, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

int[] depths = { 4, 1 };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Counting,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
boxGoTwo = CreateBlock(new Vector3(3.1f, 0f, 3.1f), k_Tag1, "box2");
boxGoThree = CreateBlock(new Vector3(2.9f, 0f, 2.9f), k_Tag2, "box2");

float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 2, output.Length);
Assert.AreEqual(10 * 10 * 2, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
}
}

8
com.unity.ml-agents.extensions/Tests/Editor/Sensors/CountingGridSensorShapeTests.cs


{
GameObject testGo;
CountingGridSensor gridSensor;
GridSensorComponent gridSensorComponent;
[SetUp]
public void SetupScene()

gridSensor = testGo.AddComponent<CountingGridSensor>();
gridSensorComponent = testGo.AddComponent<GridSensorComponent>();
}
[TearDown]

string[] tags = { "block" };
int[] depths = { 1, 1 };
Color[] colors = { Color.magenta };
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Counting, 1f, 1f, 10, 10, LayerMask.GetMask("Default"), false, colors);
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel, 1f, 1f, 10, 10, LayerMask.GetMask("Default"), false, colors);
gridSensorComponent.CreateSensors();
}
}
}

35
com.unity.ml-agents.extensions/Tests/Editor/Sensors/GridObservationPerceiveTests.cs


{
GameObject testGo;
GameObject boxGo;
GridSensor gridSensor;
GridSensorComponent gridSensorComponent;
// Use built-in tags
const string k_Tag1 = "Player";

{
testGo = new GameObject("test");
testGo.transform.position = Vector3.zero;
gridSensor = testGo.AddComponent<GridSensor>();
gridSensorComponent = testGo.AddComponent<GridSensorComponent>();
boxGo = new GameObject("block");
boxGo.tag = k_Tag1;

Object.DestroyImmediate(boxGo);
Object.DestroyImmediate(testGo);
}
[UnityTest]
public IEnumerator PerceiveNotSelfChannelHot()

string[] tags = { k_Tag2, k_Tag1 };
int[] depths = { 3 };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.ChannelHot,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.ChannelHot,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 3, output.Length);
Assert.AreEqual(10 * 10 * 3, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

string[] tags = { k_Tag2, k_Tag1 };
int[] depths = { 3 };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 1, output.Length);
Assert.AreEqual(10 * 10 * 1, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
[UnityTest]

string[] tags = { k_Tag1 };
int[] depths = { 3 };
Color[] colors = { Color.red, Color.magenta };
gridSensor.SetParameters(tags, depths, GridSensor.GridDepthType.Channel,
GridObsTestUtils.SetComponentParameters(gridSensorComponent, tags, depths, GridDepthType.Channel,
gridSensor.Start();
var gridSensor = (GridSensor)gridSensorComponent.CreateSensors()[0];
float[] output = gridSensor.Perceive();
gridSensor.Perceive();
Assert.AreEqual(10 * 10 * 1, output.Length);
Assert.AreEqual(10 * 10 * 1, gridSensor.m_PerceptionBuffer.Length);
GridObsTestUtils.AssertSubarraysAtIndex(output, subarrayIndicies, expectedSubarrays, expectedDefault);
GridObsTestUtils.AssertSubarraysAtIndex(gridSensor.m_PerceptionBuffer, subarrayIndicies, expectedSubarrays, expectedDefault);
}
}
}

14
com.unity.ml-agents.extensions/Tests/Editor/Sensors/GridSensorTestUtils.cs


using NUnit.Framework;
using System;
using System.Linq;
using Unity.MLAgents.Extensions.Sensors;
using UnityEngine;
namespace Unity.MLAgents.Extensions.Tests.Sensors
{

}
}
public static void SetComponentParameters(GridSensorComponent gridComponent, string[] detectableObjects, int[] channelDepth, GridDepthType gridDepthType,
float cellScaleX, float cellScaleZ, int gridWidth, int gridHeight, int observeMaskInt, bool rotateWithAgent, Color[] debugColors)
{
gridComponent.DetectableObjects = detectableObjects;
gridComponent.ChannelDepth = channelDepth;
gridComponent.DepthType = gridDepthType;
gridComponent.CellScale = new Vector3(cellScaleX, 0.01f, cellScaleZ);
gridComponent.GridNumSide = new Vector3Int(gridWidth, 1, gridHeight);
gridComponent.ObserveMask = observeMaskInt;
gridComponent.RotateWithAgent = rotateWithAgent;
gridComponent.DebugColors = debugColors;
}
}
}

50
com.unity.ml-agents.extensions/Tests/Utils/GridObsTestComponents/SimpleTestGridSensor.cs


using UnityEngine;
using Unity.MLAgents.Sensors;
using Unity.MLAgents.Extensions.Sensors;
namespace Unity.MLAgents.Extensions.TestUtils.Sensors

public SimpleTestGridSensor(
string name,
Vector3 cellScale,
Vector3Int gridNumSide,
bool rotateWithAgent,
int[] channelDepth,
string[] detectableObjects,
LayerMask observeMask,
GridDepthType depthType,
GameObject root,
SensorCompressionType compression,
int maxColliderBufferSize,
int initialColliderBufferSize
) : base(
name,
cellScale,
gridNumSide,
rotateWithAgent,
channelDepth,
detectableObjects,
observeMask,
depthType,
root,
compression,
maxColliderBufferSize,
initialColliderBufferSize)
{ }
}
}
public class SimpleTestGridSensorComponent : GridSensorComponent
{
public override ISensor[] CreateSensors()
{
m_Sensor = new SimpleTestGridSensor(
SensorName,
CellScale,
GridNumSide,
RotateWithAgent,
ChannelDepth,
DetectableObjects,
ObserveMask,
DepthType,
RootReference,
CompressionType,
MaxColliderBufferSize,
InitialColliderBufferSize
);
return new ISensor[] { m_Sensor };
}
}
}

121
com.unity.ml-agents.extensions/Editor/GridSensorComponentEditor.cs


using UnityEditor;
using UnityEngine;
using Unity.MLAgents.Editor;
using Unity.MLAgents.Extensions.Sensors;
namespace Unity.MLAgents.Extensions.Editor
{
[CustomEditor(typeof(GridSensorComponent))]
[CanEditMultipleObjects]
internal class GridSensorComponentEditor : UnityEditor.Editor
{
public override void OnInspectorGUI()
{
var so = serializedObject;
so.Update();
// Drawing the GridSensorComponent
EditorGUI.BeginChangeCheck();
EditorGUI.BeginDisabledGroup(!EditorUtilities.CanUpdateModelProperties());
{
// These fields affect the sensor order or observation size,
// So can't be changed at runtime.
EditorGUILayout.PropertyField(so.FindProperty(nameof(GridSensorComponent.m_SensorName)), true);
EditorGUILayout.LabelField("Grid Settings", EditorStyles.boldLabel);
EditorGUILayout.PropertyField(so.FindProperty(nameof(GridSensorComponent.m_CellScale)), true);
// We only supports 2D GridSensor now so display gridNumSide as Vector2
var gridNumSide = so.FindProperty(nameof(GridSensorComponent.m_GridNumSide));
var gridNumSide2d = new Vector2Int(gridNumSide.vector3IntValue.x, gridNumSide.vector3IntValue.z);
var newGridNumSide = EditorGUILayout.Vector2IntField("Grid Num Side", gridNumSide2d);
gridNumSide.vector3IntValue = new Vector3Int(newGridNumSide.x, 1, newGridNumSide.y);
EditorGUILayout.PropertyField(so.FindProperty(nameof(GridSensorComponent.m_RootReference)), true);
}
EditorGUI.EndDisabledGroup();
EditorGUILayout.PropertyField(so.FindProperty(nameof(GridSensorComponent.m_RotateWithAgent)), true);
EditorGUI.BeginDisabledGroup(!EditorUtilities.CanUpdateModelProperties());
{
EditorGUILayout.LabelField("Channel Settings", EditorStyles.boldLabel);
EditorGUILayout.PropertyField(so.FindProperty(nameof(GridSensorComponent.m_DepthType)), true);
// channel depth
var channelDepth = so.FindProperty(nameof(GridSensorComponent.m_ChannelDepth));
var newDepth = EditorGUILayout.IntField("Channel Depth", channelDepth.arraySize);
if (newDepth != channelDepth.arraySize)
{
channelDepth.arraySize = newDepth;
}
EditorGUI.indentLevel++;
for (var i = 0; i < channelDepth.arraySize; i++)
{
var objectTag = channelDepth.GetArrayElementAtIndex(i);
EditorGUILayout.PropertyField(objectTag, new GUIContent("Channel " + i + " Depth"), true);
}
EditorGUI.indentLevel--;
// detectable objects
var detectableObjects = so.FindProperty(nameof(GridSensorComponent.m_DetectableObjects));
var newSize = EditorGUILayout.IntField("Detectable Objects", detectableObjects.arraySize);
if (newSize != detectableObjects.arraySize)
{
detectableObjects.arraySize = newSize;
}
EditorGUI.indentLevel++;
for (var i = 0; i < detectableObjects.arraySize; i++)
{
var objectTag = detectableObjects.GetArrayElementAtIndex(i);
EditorGUILayout.PropertyField(objectTag, new GUIContent("Tag " + i), true);
}
EditorGUI.indentLevel--;
EditorGUILayout.LabelField("Collider and Buffer", EditorStyles.boldLabel);
EditorGUILayout.PropertyField(so.FindProperty(nameof(GridSensorComponent.m_MaxColliderBufferSize)), true);
EditorGUILayout.PropertyField(so.FindProperty(nameof(GridSensorComponent.m_InitialColliderBufferSize)), true);
}
EditorGUI.EndDisabledGroup();
EditorGUILayout.PropertyField(so.FindProperty(nameof(GridSensorComponent.m_ObserveMask)), true);
EditorGUI.BeginDisabledGroup(!EditorUtilities.CanUpdateModelProperties());
{
EditorGUILayout.LabelField("Sensor Settings", EditorStyles.boldLabel);
EditorGUILayout.PropertyField(so.FindProperty(nameof(GridSensorComponent.m_ObservationStacks)), true);
}
EditorGUI.EndDisabledGroup();
EditorGUILayout.PropertyField(so.FindProperty(nameof(GridSensorComponent.m_CompressionType)), true);
EditorGUILayout.LabelField("Debug Gizmo", EditorStyles.boldLabel);
EditorGUILayout.PropertyField(so.FindProperty(nameof(GridSensorComponent.m_ShowGizmos)), true);
EditorGUILayout.PropertyField(so.FindProperty(nameof(GridSensorComponent.m_GizmoYOffset)), true);
// detectable objects
var debugColors = so.FindProperty(nameof(GridSensorComponent.m_DebugColors));
var detectableObjectSize = so.FindProperty(nameof(GridSensorComponent.m_DetectableObjects)).arraySize;
if (detectableObjectSize != debugColors.arraySize)
{
debugColors.arraySize = detectableObjectSize;
}
EditorGUI.indentLevel++;
for (var i = 0; i < debugColors.arraySize; i++)
{
var debugColor = debugColors.GetArrayElementAtIndex(i);
EditorGUILayout.PropertyField(debugColor, new GUIContent("Tag " + i + " Color"), true);
}
EditorGUI.indentLevel--;
var requireSensorUpdate = EditorGUI.EndChangeCheck();
so.ApplyModifiedProperties();
if (requireSensorUpdate)
{
UpdateSensor();
}
}
void UpdateSensor()
{
var sensorComponent = serializedObject.targetObject as GridSensorComponent;
sensorComponent?.UpdateSensor();
}
}
}

11
com.unity.ml-agents.extensions/Editor/GridSensorComponentEditor.cs.meta


fileFormatVersion: 2
guid: 62dc58d0ddf584affa1f269e9c5791c2
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

286
com.unity.ml-agents.extensions/Runtime/Sensors/GridSensorComponent.cs


using UnityEngine;
using Unity.MLAgents.Sensors;
namespace Unity.MLAgents.Extensions.Sensors
{
/// <summary>
/// A SensorComponent that creates a <see cref="GridSensor"/>.
/// </summary>
[AddComponentMenu("ML Agents/Grid Sensor", (int)MenuGroup.Sensors)]
public class GridSensorComponent : SensorComponent
{
protected GridSensor m_Sensor;
[HideInInspector, SerializeField]
internal string m_SensorName = "GridSensor";
// <summary>
/// Name of the generated <see cref="GridSensor"/> object.
/// Note that changing this at runtime does not affect how the Agent sorts the sensors.
/// </summary>
public string SensorName
{
get { return m_SensorName; }
set { m_SensorName = value; }
}
[HideInInspector, SerializeField]
internal Vector3 m_CellScale = new Vector3(1f, 0.01f, 1f);
/// <summary>
/// The scale of each grid cell.
/// Note that changing this after the sensor is created has no effect.
/// </summary>
public Vector3 CellScale
{
get { return m_CellScale; }
set { m_CellScale = value; }
}
[HideInInspector, SerializeField]
internal Vector3Int m_GridNumSide = new Vector3Int(16, 1, 16);
/// <summary>
/// The number of grid on each side.
/// Note that changing this after the sensor is created has no effect.
/// </summary>
public Vector3Int GridNumSide
{
get { return m_GridNumSide; }
set
{
if (value.y != 1)
{
m_GridNumSide = new Vector3Int(value.x, 1, value.z);
}
else
{
m_GridNumSide = value;
}
}
}
[HideInInspector, SerializeField]
internal bool m_RotateWithAgent = true;
/// <summary>
/// Rotate the grid based on the direction the agent is facing.
/// </summary>
public bool RotateWithAgent
{
get { return m_RotateWithAgent; }
set { m_RotateWithAgent = value; }
}
[HideInInspector, SerializeField]
internal int[] m_ChannelDepth = new int[] { 1 };
/// <summary>
/// Array holding the depth of each channel.
/// Note that changing this after the sensor is created has no effect.
/// </summary>
public int[] ChannelDepth
{
get { return m_ChannelDepth; }
set { m_ChannelDepth = value; }
}
[HideInInspector, SerializeField]
internal string[] m_DetectableObjects;
/// <summary>
/// List of tags that are detected.
/// Note that changing this after the sensor is created has no effect.
/// </summary>
public string[] DetectableObjects
{
get { return m_DetectableObjects; }
set { m_DetectableObjects = value; }
}
[HideInInspector, SerializeField]
internal LayerMask m_ObserveMask;
/// <summary>
/// The layer mask.
/// </summary>
public LayerMask ObserveMask
{
get { return m_ObserveMask; }
set { m_ObserveMask = value; }
}
[HideInInspector, SerializeField]
internal GridDepthType m_DepthType = GridDepthType.Channel;
/// <summary>
/// The data layout that the grid should output.
/// Note that changing this after the sensor is created has no effect.
/// </summary>
public GridDepthType DepthType
{
get { return m_DepthType; }
set { m_DepthType = value; }
}
[HideInInspector, SerializeField]
internal GameObject m_RootReference;
/// <summary>
/// The reference of the root of the agent. This is used to disambiguate objects with the same tag as the agent. Defaults to current GameObject.
/// Note that changing this after the sensor is created has no effect.
/// </summary>
public GameObject RootReference
{
get { return m_RootReference == null ? gameObject : m_RootReference; }
set { m_RootReference = value; }
}
[HideInInspector, SerializeField]
internal int m_MaxColliderBufferSize = 500;
/// <summary>
/// The absolute max size of the Collider buffer used in the non-allocating Physics calls. In other words
/// the Collider buffer will never grow beyond this number even if there are more Colliders in the Grid Cell.
/// Note that changing this after the sensor is created has no effect.
/// </summary>
public int MaxColliderBufferSize
{
get { return m_MaxColliderBufferSize; }
set { m_MaxColliderBufferSize = value; }
}
[HideInInspector, SerializeField]
internal int m_InitialColliderBufferSize = 4;
/// <summary>
/// The Estimated Max Number of Colliders to expect per cell. This number is used to
/// pre-allocate an array of Colliders in order to take advantage of the OverlapBoxNonAlloc
/// Physics API. If the number of colliders found is >= InitialColliderBufferSize the array
/// will be resized to double its current size. The hard coded absolute size is 500.
/// Note that changing this after the sensor is created has no effect.
/// </summary>
public int InitialColliderBufferSize
{
get { return m_InitialColliderBufferSize; }
set { m_InitialColliderBufferSize = value; }
}
[HideInInspector, SerializeField]
internal Color[] m_DebugColors;
/// <summary>
/// Array of Colors used for the grid gizmos.
/// </summary>
public Color[] DebugColors
{
get { return m_DebugColors; }
set { m_DebugColors = value; }
}
[HideInInspector, SerializeField]
internal float m_GizmoYOffset = 0f;
/// <summary>
/// The height of the gizmos grid.
/// </summary>
public float GizmoYOffset
{
get { return m_GizmoYOffset; }
set { m_GizmoYOffset = value; }
}
[HideInInspector, SerializeField]
internal bool m_ShowGizmos = false;
/// <summary>
/// Whether to show gizmos or not.
/// </summary>
public bool ShowGizmos
{
get { return m_ShowGizmos; }
set { m_ShowGizmos = value; }
}
[HideInInspector, SerializeField]
internal SensorCompressionType m_CompressionType = SensorCompressionType.PNG;
/// <summary>
/// The compression type to use for the sensor.
/// </summary>
public SensorCompressionType CompressionType
{
get { return m_CompressionType; }
set { m_CompressionType = value; UpdateSensor(); }
}
[HideInInspector, SerializeField]
[Range(1, 50)]
[Tooltip("Number of frames of observations that will be stacked before being fed to the neural network.")]
internal int m_ObservationStacks = 1;
/// <summary>
/// Whether to stack previous observations. Using 1 means no previous observations.
/// Note that changing this after the sensor is created has no effect.
/// </summary>
public int ObservationStacks
{
get { return m_ObservationStacks; }
set { m_ObservationStacks = value; }
}
/// <inheritdoc/>
public override ISensor[] CreateSensors()
{
m_Sensor = new GridSensor(
m_SensorName,
m_CellScale,
m_GridNumSide,
m_RotateWithAgent,
m_ChannelDepth,
m_DetectableObjects,
m_ObserveMask,
m_DepthType,
RootReference,
m_CompressionType,
m_MaxColliderBufferSize,
m_InitialColliderBufferSize
);
if (ObservationStacks != 1)
{
return new ISensor[] { new StackingSensor(m_Sensor, ObservationStacks) };
}
return new ISensor[] { m_Sensor };
}
/// <summary>
/// Update fields that are safe to change on the Sensor at runtime.
/// </summary>
internal void UpdateSensor()
{
if (m_Sensor != null)
{
m_Sensor.CompressionType = m_CompressionType;
}
}
void OnDrawGizmos()
{
if (m_ShowGizmos)
{
if (m_Sensor == null)
{
return;
}
var cellColors = m_Sensor.PerceiveGizmoColor();
var cellPositions = m_Sensor.GetGizmoPositions();
var rotation = m_Sensor.GetGridRotation();
var scale = new Vector3(m_CellScale.x, 1, m_CellScale.z);
var gizmoYOffset = new Vector3(0, m_GizmoYOffset, 0);
var oldGizmoMatrix = Gizmos.matrix;
for (var i = 0; i < cellPositions.Length; i++)
{
var cubeTransform = Matrix4x4.TRS(cellPositions[i] + gizmoYOffset, rotation, scale);
Gizmos.matrix = oldGizmoMatrix * cubeTransform;
var colorIndex = cellColors[i];
var debugRayColor = Color.white;
if (colorIndex > -1 && m_DebugColors.Length > colorIndex)
{
debugRayColor = m_DebugColors[colorIndex];
}
Gizmos.color = new Color(debugRayColor.r, debugRayColor.g, debugRayColor.b, .5f);
Gizmos.DrawCube(Vector3.zero, Vector3.one);
}
Gizmos.matrix = oldGizmoMatrix;
}
}
}
}

114
com.unity.ml-agents.extensions/Runtime/Sensors/CountingGridSensor.cs


using System;
using UnityEngine;
namespace Unity.MLAgents.Extensions.Sensors
{
public class CountingGridSensor : GridSensor
{
/// <inheritdoc/>
public override void InitDepthType()
{
ObservationPerCell = ChannelDepth.Length;
}
/// <summary>
/// Overrides the initialization ofthe m_ChannelHotDefaultPerceptionBuffer with 0s
/// as the counting grid sensor starts within its initialization equal to 0
/// </summary>
public override void InitChannelHotDefaultPerceptionBuffer()
{
m_ChannelHotDefaultPerceptionBuffer = new float[ObservationPerCell];
}
/// <inheritdoc/>
public override void SetParameters(string[] detectableObjects, int[] channelDepth, GridDepthType gridDepthType,
float cellScaleX, float cellScaleZ, int gridWidth, int gridHeight, int observeMaskInt, bool rotateToAgent, Color[] debugColors)
{
this.ObserveMask = observeMaskInt;
this.DetectableObjects = detectableObjects;
this.ChannelDepth = channelDepth;
if (DetectableObjects.Length != ChannelDepth.Length)
throw new UnityAgentsException("The channels of a CountingGridSensor is equal to the number of detectableObjects");
this.gridDepthType = gridDepthType;
this.CellScaleX = cellScaleX;
this.CellScaleZ = cellScaleZ;
this.GridNumSideX = gridWidth;
this.GridNumSideZ = gridHeight;
this.RotateToAgent = rotateToAgent;
this.DiffNumSideZX = (GridNumSideZ - GridNumSideX);
this.OffsetGridNumSide = (GridNumSideZ - 1f) / 2f;
this.DebugColors = debugColors;
}
/// <summary>
/// For each collider, calls LoadObjectData on the gameobejct
/// </summary>
/// <param name="foundColliders">The array of colliders</param>
/// <param name="cellIndex">The cell index the collider is in</param>
/// <param name="cellCenter">the center of the cell the collider is in</param>
protected override void ParseColliders(Collider[] foundColliders, int numFound, int cellIndex, Vector3 cellCenter)
{
GameObject currentColliderGo = null;
Vector3 closestColliderPoint = Vector3.zero;
for (int i = 0; i < numFound; i++)
{
currentColliderGo = foundColliders[i].gameObject;
// Continue if the current collider go is the root reference
if (currentColliderGo == rootReference)
continue;
closestColliderPoint = foundColliders[i].ClosestPointOnBounds(cellCenter);
LoadObjectData(currentColliderGo, cellIndex,
Vector3.Distance(closestColliderPoint, transform.position) * InverseSphereRadius);
}
}
/// <summary>
/// Throws an execption as this should not be called from the CountingGridSensor class
/// </summary>
/// <param name="currentColliderGo">The current gameobject to get data from</param>
/// <param name="typeIndex">the index of the detectable tag of this gameobject</param>
/// <param name="normalizedDistance">The normalized distance to the gridsensor</param>
/// <returns></returns>
protected override float[] GetObjectData(GameObject currentColliderGo, float typeIndex, float normalizedDistance)
{
throw new Exception("GetObjectData isn't called within the CountingGridSensor");
}
/// <summary>
/// Adds 1 to the counting index for this gameobject of this type
/// </summary>
/// <param name="currentColliderGo">the current game object</param>
/// <param name="cellIndex">the index of the cell</param>
/// <param name="normalizedDistance">the normalized distance from the gameobject to the sensor</param>
protected override void LoadObjectData(GameObject currentColliderGo, int cellIndex, float normalizedDistance)
{
for (int i = 0; i < DetectableObjects.Length; i++)
{
if (currentColliderGo != null && currentColliderGo.CompareTag(DetectableObjects[i]))
{
if (ShowGizmos)
{
Color debugRayColor = Color.white;
if (DebugColors.Length > 0)
{
debugRayColor = DebugColors[i];
}
CellActivity[cellIndex] = new Color(debugRayColor.r, debugRayColor.g, debugRayColor.b, .5f);
}
/// <remarks>
/// The observations are "channel count" so each grid is WxHxC where C is the number of tags
/// This means that each value channelValues[i] is a counter of gameobject included into grid cells where i is the index of the tag in DetectableObjects
/// </remarks>
int countIndex = cellIndex * ObservationPerCell + i;
m_PerceptionBuffer[countIndex] = Mathf.Min(1f, m_PerceptionBuffer[countIndex] + 1f / ChannelDepth[i]);
break;
}
}
}
}
}

/com.unity.ml-agents.extensions/Runtime/Sensors/CountingGridSensor.cs.meta → /com.unity.ml-agents.extensions/Runtime/Sensors/GridSensorComponent.cs.meta

正在加载...
取消
保存