Original documentation: https://github.com/allenai/ai2thor
Machine Common Sense documentation: https://nextcenturycorporation.github.io/MCS/
The CACI development team has worked on this Unity project with version 2019.4.X of the Unity Editor on both Linux and Mac.
Note for Linux developers: Our current fork of AI2-THOR has been upgraded to v2.5.0 and is configured to use Unity Editor version 2019.4.20
, but that version was not available for the Linux Unity Editor. However, version 2019.4.0f1
does work fine. Note that the Unity Hub download from Unity's Downloads page may not actually work on Linux (see the Linux Installation Instructions below).
Note that while installing and/or launching Unity, you may get an error about libgconf-2.so.4
. You should be able to solve this issue by sudo apt install
-ing the library.
-
Download the
2019.4.0f1
"Official Installer" from the Unity Linux Editor forums here. The download is calledUnitySetup-2019.4.0f1
. -
Run the
UnitySetup-2019.4.0f1
executable (you may need tochmod
it). This should install aUnity-2019.4.0f1
folder. -
In
Unity-2019.4.0f1/Editor/
run theUnity
executable to start the Unity Hub. -
Enter your MCS Unity License info into the Unity Hub.
-
In the Unity Hub, under the Projects tab, click Open and select the
/unity/
folder in your local clone of this repository. This should add a "unity" project to your Projects list. -
Double-click the "unity" project to launch the Unity Editor. See Run below for usage information. Please note that the initial load of this project in the Unity Editor will take a long time.
To setup pre-commit, in the root directory run these commands:
pip install pre-commit
- For Mac
brew install clang-format-16
for Linuxapt-get install clang-format-16
pre-commit install
If the global installation does not work, try setting up a virtual environment and follow these instructions instead:
python3 -m venv --prompt unity venv
source venv/bin/activate
pip install pre-commit
sudo apt-get remove clang-format
wget https://apt.llvm.org/llvm.sh
chmod +x llvm.sh
sudo ./llvm.sh 16
sudo apt-get install clang-format-16
sudo update-alternatives --install /usr/bin/clang-format clang-format /usr/bin/clang-format-16 100
rm llvm.sh
pre-commit install
CACI employees and subcontractors: Checkout the MCS private GitHub repository and copy the files from its UnityAssetStore
folder into unity/Assets/Addressables/MCS/UnityAssetStore/
.
Non-CACI employees: Please continue with the rest of these instructions.
To enable debug logging in your Unity builds, open the Player Settings (Edit->Project Settings, then click on the Player tab), then add ENABLE_DEBUG_LOGS to "Scripting Define Symbols" under "Other Settings" (please note that each symbol in the list should be separated by a semicolon), and hit ENTER to ensure that Unity saved your change.
If you want to run an MCS Scene in the Unity Editor:
-
Open the MCS Scene:
File->Open Scene
then selectAssets/Scenes/MCS-Starter-Scene.unity
-
By default, in the Unity Editor, see the Hierarchy window on the left, the Scene and Game windows in the middle, the Inspector window on the right, and the Project and Console windows at the bottom.
- The Hierarchy window lists the Game Objects in the Scene.
- The Scene and Game windows show the Scene.
- The Inspector window lists the properties, scripts, materials, and other components of the selected Game Object.
- The Project window shows the files in the current project.
- The Console window shows the logs and errors.
-
To successfully run an MCS Scene, copy a JSON scene configuration file from the scenes folder in our MCS GitHub repository into the
unity/Assets/Addressables/MCS/Scenes/
folder, or identify a JSON file in the folder to use (likeplayroom.json
). -
Click on the
Util-Loader-Obj
Game Object in the Hierarchy window. Then, in the Inspector Window, under theAddressable Scene Loader (Script)
component, enter the name of your selected JSON file in the"Default Scene File"
property WITHOUT the.json
extension. -
If you want to see the class/depth/object masks, click on the
FPSController->FirstPersonCharacter
Game Object in the Hierarchy window, then toggle-on the checkbox next to theImage Synthesis (Script)
component in the Inspector window to activate that script. You can see the masks during a run using the Display dropdown in the Game window. -
Click the Play button in the top center of the Unity Editor to run the Scene. See the list of keys and parameters below. To set action parameters, click the
FPSController
Game Object in the Hierarchy window, then use the inputs underDebug Discrete Agent Controller (Script)
. Seeunity/Assets/Scripts/DebugDiscreteAgentController.cs
for additional key bindings.
(See bullet 6 above)
- W/A/S/D: Move
- R: Look/Rotate
- Rotate
- O: Open Object
- Receptacle Object ID
- Receptacle Object Direction (instead of using an object ID)
- C: Close Object
- Receptacle Object ID (second object to put the held object onto)
- Receptacle Object Direction (instead of using an object ID)
- P: Pickup Object
- Move Or Pickup Object ID (for the held object)
- Move Or Pickup Object Direction (instead of using an object ID)
- Z: Put (held) Object (onto an object)
- Move Or Pickup Object ID (for the held object)
- Move Or Pickup Object Direction (instead of using an object ID)
- Receptacle Object ID (second object to put the held object onto)
- Receptacle Object Direction (instead of using an object ID)
- X: Drop Object
- Move Or Pickup Object ID (for the held object)
- Move Or Pickup Object Direction (instead of using an object ID)
- U: Push or Pull Object
- Move Or Pickup Object ID
- Move Or Pickup Object Direction (instead of using an object ID)
- Push Pull Force (positive is push, negative is pull)
- B: Torque Object
- Move Or Pickup Object ID
- Move Or Pickup Object Direction (instead of using an object ID)
- Push Pull Force (positive is clockwise torque, negative is counterclockwise torque)
- N: Rotate Object
- Move Or Pickup Object ID
- Move Or Pickup Object Direction (instead of using an object ID)
- Direction (clockwise true is a clockwise rotation, clockwise false is a counterclockwise rotation)
- M: Move Object
- Move Or Pickup Object ID
- Move Or Pickup Object Direction (instead of using an object ID)
- Lateral (Relative to where the agent is looking, -1 for left movement, 0 is no movement, 1 for right movement)
- Straight (Relative to where the agent is looking, -1 for back movement, 0 is no movement, 1 for forward movement)
- Escape: Pass (do nothing)
- Backspace: Initialize (reset the current scene or go to a new scene)
- New Scene File
Open the Unity Editor and build the project with File->Build Settings
. Check Development Mode
and Script Debugging
for detailed debug logging (but do NOT check these for any public release builds!).
Alternatively, if you want to build the Unity project via the command line, run the command below, replacing the path to your Unity executable file, log file name, <cloned_repository>
, and the executeMethod
as needed. Please note that this command will build ALL the AI2-THOR scenes which will take a very long time (my only solution was to delete all the AI2-THOR scenes with rm <cloned_repository>/unity/Assets/Scenes/FloorPlan*
).
./Unity-2019.4.0f1/Editor/Unity -quit -batchmode -logfile MCS-Unity-Build.log -projectpath <cloned_repository>/unity/ -executeMethod Build.Linux64
To TAR the application's Data directory:
cd <cloned_repository>/unity/
tar -czvf MCS-AI2-THOR-Unity-App-<version>_Data.tar.gz MCS-AI2-THOR-Unity-App-<version>_Data/
(Please note that this list has not been kept up-to-date.)
unity/
The MCS Unity project. Add this folder as a project in your Unity Hub.unity/Assets/Scenes/MCS.unity
The MCS Unity Scene. You can load and edit this in the Unity Editor.unity/Assets/Scripts/MachineCommonSenseConfig.cs
A class with MCS config data: the "material registry", which lists Materials that may be loaded at runtime in the MCS scene; the "material colors", which maps Material names to color words.unity/Assets/Scripts/MachineCommonSenseMain.cs
The main MCS Unity script that is imported into and runs within the Scene.unity/Assets/Scripts/MachineCommonSenseController.cs
A custom subclass extending AI2-THOR's PhysicsRemoteFPSAgentController that handles player actions and state.unity/Assets/Scripts/MachineCommonSensePerformerManager.cs
A custom subclass extending AI2-THOR's AgentManager that handles the communication between the Python API and the Unity Scene.unity/Assets/Scripts/MachineCommonSenseSceneManager.cs
A custom subclass extending AI2-THOR's PhysicsSceneManager that handles scene state.unity/Assets/Addressables/MCS/
Folder containing all MCS runtime resources.unity/Assets/Addressables/MCS/ai2thor_object_registry.json
Config file containing the MCS Scene's specific Game Objects borrowed from the AI2-THOR framework that may be loaded at runtime.unity/Assets/Addressables/MCS/mcs_object_registry.json
Config file containing the MCS Scene's specific custom Game Objects that may be loaded at runtime.unity/Assets/Addressables/MCS/primitive_object_registry.json
Config file containing the MCS Scene's Unity Primitive Game Objects that may be loaded at runtime.unity/Assets/Addressables/MCS/Materials/
This is a copy of AI2-THOR'sunity/Assets/QuickMaterials/
folder. We had to copy it over to theAddressables
folder (and save it in our repo) to load the assets at runtime.unity/Assets/Addressables/MCS/Scenes/
Folder containing sample scene config files (see Run).
(Please note that this list has not been kept up-to-date.)
- The
FPSController
object is mostly the same, but I made it smaller to simulate a baby. This also allowed me to downscale the room which not only improves performance but also was necessary to get the depth masks to work (while standing at one end of the room, you still want to see the far wall in the depth masks). Changes affected theTransform
,Character Controller
, andCapsule Collider
in theFPSController
and theTransform
in theFirstPersonCharacter
(camera) nested inside theFPSController
. - In the
FPSController
object, I replaced thePhysicsRemoteFPSAgentController
andStochasticRemoteFPSAgentController
scripts with ourMachineCommonSensePerformerManager
script. - In the
PhysicsSceneManager
object, I replaced theAgentManager
script with ourMachineCommonSensePerformerManager
script. - Added structural objects (walls, floor, ceiling).
- Added the invisible
MCS
object containing ourMachineCommonSenseMain
script that runs in the background. - The
FPSController
prefab now has the AgentHand at the top level (instead of underFirstPersonCharacter
), so that it is no longer affected by head tilt/camera.
- (Unity)
BaseFPSAgentController.ProcessControlCommand
will useInvoke
to call the specific action function inBaseFPSAgentController
orPhysicsRemoteFPSAgentController
(likeMoveAhead
orLookUp
) - (Unity) The specific action function will call
BaseFPSAgentController.actionFinished()
to setactionComplete
totrue
- (Python) You create a new Python AI2-THOR
Controller
object - (Python) The
Controller
class constructor will automatically send aReset
action over the AI2-THOR socket toAgentManager.ProcessControlCommand(string action)
- (Unity)
AgentManager.ProcessControlCommand
will create aServerAction
from the action string and callAgentManager.Reset(ServerAction action)
to load the MCS Unity scene - (Python) You call
controller.step(dict action)
with anInitialize
action to load new MCS scene configuration JSON data and re-initialize the player - (Unity) The action is sent over the AI2-THOR socket to
AgentManager.ProcessControlCommand(string action)
- (Unity)
AgentManager.ProcessControlCommand
will create aServerAction
from the action string and callAgentManager.Initialize(ServerAction action)
- (Unity)
AgentManager.Initialize
will callAgentManager.addAgents(ServerAction action)
, then callAgentManager.addAgent(ServerAction action)
, then callBaseFPSAgentController.ProcessControlCommand(ServerAction action)
with theInitialize
action - (Unity) See the Shared Workflow
- (Unity)
AgentManager.LateUpdate
, which is run every frame, will seeactionComplete
istrue
and callAgentManager.EmitFrame()
- (Unity)
AgentManager.EmitFrame
will return output from theInitialize
action to the Python API (controller.step
) and await the next action - (Python) You call
controller.step(dict action)
with a specific action - (Unity) The action is sent over the AI2-THOR socket to
AgentManager.ProcessControlCommand(string action)
- (Unity)
AgentManager.ProcessControlCommand
will create aServerAction
from the action string and callBaseFPSAgentController.ProcessControlCommand(ServerAction action)
(except onReset
orInitialize
actions) - (Unity) See the Shared Workflow
- (Unity)
AgentManager.LateUpdate
, which is run every frame, will seeactionComplete
istrue
and callAgentManager.EmitFrame()
- (Unity)
AgentManager.EmitFrame
will return output from the specific action to the Python API (controller.step
) and await the next action
- (Unity) Loads the Unity scene
- (Editor) Waits until you press a key
- (Unity)
DebugDiscreteAgentController.Update
, which is run every frame, will create aServerAction
from the key you pressed and callBaseFPSAgentController.ProcessControlCommand(SeverAction action)
- (Unity) See the Shared Workflow
- (Unity)
DebugDiscreteAgentController.Update
will seeactionComplete
istrue
and then waits until you press another key
- Adding AI2-THOR's custom Tags and Layers to your Game Objects is needed for their scripts to work properly. For example, if you don't tag the walls as
Structure
, then the player can walk fully into them. - Fast moving objects that use Unity physics, as well as all structural objects, should have their
Collision Detection
(in theirRigidbody
) set toContinuous
. With these changes, a fast moving object that tries to move from one side of a wall to the other side in a single frame will be stopped as expected. - The FPSController object's robot model is half scale, and ends up being about 0.5 high while the game is running. I had to change the properties of the
Capsule Collider
and theCharacter Controller
so the FPSController would not collide with the floor while moving (PhysicsRemoteFPSAgentController.capsuleCastAllForAgent
). Previously:center.y=-0.45
,radius=0.175
,height=0.9
. Now:center.y=-0.05
,radius=0.2
,height=0.5
(though these numbers seem smaller than they should really be).
Simple Workflow:
- Create a Unity Prefab and save it in the
unity/Assets/Addressables/MCS/
folder. - Add the relevant scripts and subcomponents to it (see the section below).
- Add it to the
unity/Assets/Addressables/MCS/mcs_object_registry.json
file with a unique ID and a path to the prefab. - While the object is selected, the check the box at the top of the inspector window to mark object as addressable.
- Build the updated Addressables bundle.
- Rebuild the Unity application.
For a more detailed walkthrough how adding objects: https://nextcentury.atlassian.net/wiki/spaces/MCS/pages/2280161285/Adding+Content+To+Addressables
Take a GameObject (we'll call it the "Target" object) containing a MeshFilter, MeshRenderer, and material(s). Sometimes the components are on the Target itself, and sometimes they are on a child of the Target.
- Set the Tag of the Target to "SimObjPhysics" and set the Layer to "SimObjVisible".
- Add a Rigidbody to the Target. Ensure its "Use Gravity" property is true.
- If the Target (or its child) does not have any Colliders, you'll have to make them. Create an Empty Child under the Target called "Colliders" and mark it static. (AI2-THOR should be able to find colliders added to any child objects, as long as they're also set in the MyColliders property of the prefab's SimObjPhysics script.) Then create an Empty Child under "Colliders" for each Collider you need to make (give them useful names). On each child, add the correct Collider component (often a box, but sometimes others -- note that all MeshColliders should be CONVEX). Adjust the Transform of each child to position the Collider as needed. Set the Tag of each child to "SimObjPhysics" and set the Layer to "SimObjVisible".
- Create an Empty Child under the Target called "VisibilityPoints" (no space!) and mark it static. Then create an Empty Child under "VisibilityPoints" for each visibility point you need to make. Adjust the Transform of each child to position the visibility point as needed. Set the Layer of each child to "SimObjVisible". A visibility point should be positioned on each corner of the Target, plus one or more points should be positioned on each large surface (think: if all the corners are occluded, can I still draw line-of-sight to the center of the Target?).
- Create an Empty Child under the Target called "BoundingBox" (no space!) and add a BoxCollider component to it. Ensure this BoxCollider is NOT ACTIVE (but NOT the other Colliders). Adjust the Transform of the "BoundingBox" to completely enclose the Target. Set the Layer of the Target to "SimObjInvisible".
- On the Target itself, add a SimObjPhysics component (it's an AI2-THOR script). Set the "Primary Property" to "Static" (for non-moveable objects), "Moveable", or "Can Pickup" (a subset of Moveable). Set the "Secondary Properties" as needed (like "Receptacle" and/or "Can Open"). Set the "Bounding Box" property to the "BoundingBox" child you created. Set the "Visibility Points" property to the visibility point children you created. Set the "My Colliders" property to the Collider children you created. Optionally, set the "Salient Materials" property as needed.
- If the Target is openable, add a Can Open_Object component (AI2-THOR script) to the Target. Set the "Moving Parts" property to the Target. Set the "Open Positions" and the "Close Positions" to the correct positions. Change the "Movement Type" property to "Slide", "Rotate", or "Scale" as needed.
- If the Target is a Receptacle, create an Empty Child under the Target called "ReceptacleTriggerBox" (no spaces!) and mark it static. Set the Tag of the "ReceptacleTriggerBox" to "Receptacle" and set the Layer to "SimObjInvisible". Add a "BoxCollider" component to the "ReceptacleTriggerBox" and set its "Is Trigger" property to true. Adjust the Transform of the "ReceptacleTriggerBox" to the receptacle area that can contain objects (I'm not sure if the height actually matters). Add a Contains component (AI2-THOR script) to the "ReceptacleTriggerBox".
- For each other receptacle within the Target (like a cabinet door, drawer, shelf, etc.), create an Empty Child under the Target (we'll call this the Sub-Target), give it a useful name, and move the mesh corresponding to the Sub-Target to be under the child. Repeat steps 1-8 (EXCEPT the Bounding Box) on each Sub-Target.
- Click-and-drag the finished Target into the Project tab of the Unity Editor to save it as a new Prefab file. Add a new entry for it in the mcs_object_registry file.
A tool for recording of ServerActions
to a file for playback. These files can currently only be played back within the Unity editor under Tools -> ServerAction Recorder
.
Recorded files will be saved when the executable has been closed, or when the editor Play Mode
has stopped. The files will be located within the StreamingAssets -> Recording
folder.
To enable recording of a session:
-
Editor
- Add "RECORD_SERVERACTIONS" to
PlayerSettings -> Scripting Define Symbols
.
- Add "RECORD_SERVERACTIONS" to
-
Build
- Add the command line argument
-RECORD_SERVERACTIONS
to your executable.
- Add the command line argument
Location of recorded files:
- Editor
"\unity\Assets\StreamingAssets\Recordings"
- Windows/Linux
"MCS-AI2-THOR-Unity-App-v#.#.#_Data\StreamingAssets\Recordings"
- Mac
"MCS-AI2-THOR-Unity-App-v#.#.#\Resources\Data\StreamingAssets\Recordings"
For playback:
- Copy your recorded file into the editor path
"ai2thor\unity\Assets\StreamingAssets\Recordings"
- Open playback window through the toolbar
Tools -> ServerAction Recorder
- Type your recorded file name into the
File Name
text field. - Click
Load
to load the file for playback- Any errors with the file with be directly showed in the window, with exceptions showing in the
Console
window.
- Any errors with the file with be directly showed in the window, with exceptions showing in the
- Click
Play
- This will automatically start the editor with the loaded recording file.
(Please note that this list has not been kept up-to-date.)
Scripts/AgentManager
:- Added properties to
MetadataWrapper
:clippingPlaneFar
,clippingPlaneNear
,structuralObjects
- Added properties to
ObjectMetadata
:colorsFromMaterials
,direction
,distanceXZ
,heading
,points
,shape
,visibleInCamera
- Added properties to
ServerAction
:logs
,objectDirection
,receptacleObjectDirection
,sceneConfig
- Added
virtual
to functions:setReadyToEmit
,Update
- Changed variables or functions from
private
toprotected
:physicsSceneManager
, mostrender*Image
variables - Changed properties in
ServerAction
:horizon
(from int to float) - Changed variables or functions from
private
topublic
:captureScreen
, 'renderImage' - Split the existing metadata-update-behavior of the
addObjectImageForm
function into a separate, new function calledUpdateMetadataColors
- Created the
InitializeForm
andFinalizeMultiAgentMetadata
virtual functions and called them both insideEmitFrame
- Changed
readyToEmit = true;
tothis.setReadyToEmit(true);
inaddAgents
,ProcessControlCommand
,Start
- Added Object Salient Materials:
Hollow
,Undefined
- Added property
consistentColors
- Added property
physicsFramesPerSecond
- Added property
roomDimensions
- Added properties to
Scripts/BaseFPSAgentController
:- Added
virtual
to functions:Initialize
,ProcessControlCommand
- Removed the hard-coded camera properties in the
SetAgentMode
function - Replaced the call to
checkInitializeAgentLocationAction
inInitialize
with calls tosnapToGrid
andactionFinished
so re-initialization doesn't cause the player to move for a few steps - Added
lastActionStatus
toInitialize
to help indicate success or failure - Changed
nearestAngleIndex
to return the nearest index based on the minimum difference between the current angle and the angle at the index - Pulled out code for getting capsule parameters for agent from capsuleCastAllForAgent function to GetCapsuleInfoForAgent
- Added factoring in scaling scaling to collider radius (now called adjustedRadius) in capsuleCastAllForAgent
- Changed maxVisibleDistance to 1.0
- Added a 45 degree angle check for ramp ascension and descension that occurs when the agents collider is obstructed by a structure. If a capsule cast the size of the agents collider shot 45 degrees up from the base of the agent is not obstrucuted, then the agent can move sucesfully.
- Changed capusle cast obstruction checks to use a point detected by a sphere-casted shot from the center of agent directly below as the bottom base of capsule cast checks rather than the base of the agent's collider. This results in higher accruacy and avoids clipping into the floor
- Added
NOT_VISIBLE
ActionStatus. Returning this status means the object is within range for an interaction but is either obstructed or not in the agent's viewport (ex. the object is at the agent's feet but the agent is looking straight ahead). - Added
VisibilityBools
class with two booleans (inViewportAndVisible
,notInViewportButNotObstructed
).inViewportAndVisible
means that an object is in the agent's viewport and can be seen without obstruction. Examples: a ball is on the ground directly front of the agent and the agent is looking down at the ball, a ball is across an empty room and the agent is staring at the ball even though it is out of distance for an interaction.notInViewportButNotObstructed
means the object could potentially be in the agent's line of sight without obstruction but the agent's rotation makes the object not currently visible in the viewport. Examples: a ball is on the ground in directly front of the agent and the agent is staring above the ball or is turned around, a ball is across an empty room and the agent is staring the other way, even though it is out of distance for an interaction it still has the potential to be visible once the agent rotates to look at it. - In
GetAllVisibleSimObjPhysicsCollider
added support for seeing ghosted objects (objects with inactive colliders). - Added
NOT_VISIBLE
ActionStatus. Returning this status means the object is within range for an interaction but is either obstructed or not in the agent's viewport (ex. the object is at the agent's feet but the agent is looking straight ahead). - Added
VisibilityBools
class with two booleans (inViewportAndVisible
,notInViewportButNotObstructed
).inViewportAndVisible
means that an object is in the agent's viewport and can be seen without obstruction. Examples: a ball is on the ground directly front of the agent and the agent is looking down at the ball, a ball is across an empty room and the agent is staring at the ball even though it is out of distance for an interaction.notInViewportButNotObstructed
means the object could potentially be in the agent's line of sight without obstruction but the agent's rotation makes the object not currently visible in the viewport. Examples: a ball is on the ground in directly front of the agent and the agent is staring above the ball or is turned around, a ball is across an empty room and the agent is staring the other way, even though it is out of distance for an interaction it still has the potential to be visible once the agent rotates to look at it. - Added
NOT_AGENT
ActionStatus. Returning this status means the performer is callingInteractWithAgent
on an object that is not a simulation agent. - Added
AGENT_CURRENTLY_INTERACTING_WITH_PERFORMER
ActionStatus. Returning this status means the perofmer is callingInteractWithAgent
on a simulation agent that is either rotating toward the performer, playing the animation that it is not carrying the target, or holding out the target. - Added
AGENT_IS_BUSY
ActionStatus. Returning this status means the performer is callingInteractWithAgent
on an agent that is rotating toward a target or beginning its pointing animation. - Change
ItemInHand
from a GameObject to a SimObjPhysics
- Added
Scripts/CanOpen_Object
:- Rewrote part of the
Interact
function so it doesn't use iTween ifanimationTime
is0
. Also theInteract
function now uses theopenPercentage
on both "open" and "close". - Added
IsMovementTypeSlide
function - Added
separateLid
variable that is used for a lidless container that needs a reference to its separate lid that will be merged later. - Added
InteractWithLid
for interactions with a separate lid or container with a separate lid.
- Rewrote part of the
Scripts/Contains
:- Added function
RemoveFromCurrentlyContains
to temporarily get around ReceptacleObjects not updating when an object is picked up (and deactivated). - In
GetValidSpawnPoints
, rewrote the method so that it generates the spawn points based on the global UP (which may actually be down, left, right, forward, or back) rather than the receptacle object's local UP, so the grid may be X/Y, X/Z, or Y/Z. - In
CheckIfPointIsInsideReceptacleTriggerBox
, if the receptacle trigger box's parent object has theStacking
secondary property, just ensure that the point is above the receptacle trigger box's bottom Y point. - In
CheckIfPointIsInsideReceptacleTriggerBox
, fixed how the receptacle trigger box center and size are calculated so that its transform, its parent's transform(s), and its collider are all used. - Added the
FindReceptacleTriggerBoxSize
method to implemented the behavior in the previous bullet. - Removed the
CheckIfPointIsAboveReceptacleTriggerBox
method because it is no longer used (due to corresponding changes inInstantiatePrefabTest
) and is also redundant withCheckIfPointIsInsideReceptacleTriggerBox
. - Added
physicsFramesPerSecond
property
- Added function
Scripts/DebugDiscreteAgentController
:- Calls
ProcessControlCommand
on the controller object with an "Initialize" action in itsStart
function (so the Unity Editor Workflow mimics the Python API Workflow) - Added a way to "Pass" (with the "Escape" button) or "Initialize" (with the "Backspace" button) on a step while playing the game in the Unity Editor
- Added support for executing other actions and properties while playing the game in the Unity Editor
- Calls
Scripts/InstantiatePrefabTest
:- In
PlaceObject
, fixed object rotation so that it always rotates around the global DOWN rather than using the receptacle object's local rotation. - In
PlaceObject
, removed theHowManyCornersToCheck
behavior because it was buggy (there's no way to guarantee that the 4 correct corners are always the 4 bottom corners). - In
PlaceObject
, removed setting the object's rotation to the receptacle trigger box's rotation to keep the original rotation. - In
PlaceObject
, in theHowManyRotationsToCheck
loop, fixed setting the object's rotation to properly use euler angles. - In
PlaceObject
, in theToCheck
loop, fixed setting the object's target position to handle objects with non-zero rotations. - In
CheckSpawnArea
, fixed how the object bounding box center and size are calculated so that its transform, its parent's transform, and its collider are all used.
- In
Scripts/PhysicsRemoteFPSAgentController
:- Changed variables or functions from
private
toprotected
:physicsSceneManager
,ObjectMetadataFromSimObjPhysics
- Added
virtual
to functions:CloseObject
,DropHandObject
,OpenObject
,PickupObject
,PullObject
,PushObject
,PutObject
,ResetAgentHandPosition
,ThrowObject
,ToggleObject
- Commented out a block in the
PickupObject
function that checked for collisions between the held object and other objects in the scene because it caused odd behavior if you were looking at the floor. TheLook
functions don't make this check either, and we may decide not to move the held object duringLook
actions anyway. - In the
PlaceHeldObject
function: ignoresPlacementRestrictions
ifObjType
isIgnoreType
; sets the held object's parent to null so the parent's properties (like scale) don't affect the placement validation; sets the held object'sisKinematic
property tofalse
if placement is successful; fixed an issue with placing held objects inside openble receptacles. - Added the
FindClosestPoint
function. - In
ApplyForceObject
andPickupObject
, useFindClosestPoint
to decide whether an object is obstructed or just out-of-reach. - Added
lastActionStatus
to Move actions, as well as toDropHandObject
,PickupObject
, andPutObject
to help indicate success or reason for failure - Added check to make sure object exists for
DropHandObject
- Make sure objectId specified is actually the object being held for
DropHandObject
andPutObject
- Undid objectId being reset to receptableObjectId and not allowing objects to be placed in closed receptacles regardless of type of receptacle for
PutObject
- In
PickupContainedObjects
andDropContainedObjects
, added a null check for the Colliders object and added a loop over the colliders array in the SimObjPhysics script. - In
PickupContainedObjects
, don't pickup contained objects if the receptacle has theStacking
secondary property. - Added code to allow movement that will auto calculate the space to close the distance to an object within 0.1f
- In 'CheckIfAgentCanTurn' and 'CheckIfAgentCanLook' add a check to see if object in hand is active
- In
InteractAndWait
, parent objects within receptacles to that receptacle so they all move together when a receptacle is opened or closed. - Added logic to
InteractAndWait
to reset an object to its prior position if open/close action fails, and to increase the radius used to check if an agent is in the way of the object to be opened/closed. - For
OpenObject
andCloseObject
, only use coroutine if physics are enabled. - For
OpenObject
, if opening a door andrestrictOpenDoors
istrue
, lock all other doors inInteractAndWait
andOpenOrCloseObject
. - In
isAgentCapsuleCollidingWith
, added expandBy parameter. - Added
isAgentOnTopOfObject
function to check for obstructions when opening objects that slide out (like drawers). - Change the layer of the
ItemInHand
toSimObjInvisible
when picked up and toSimObjVisible
when put/dropped/thrown. - Reorganized
PlaceHeldObject
,OpenObject
, andCloseObject
to return the most relevant action status. PlaceHeldObject
,OpenObject
,CloseObject
, andApplyForceObject
now use VisibilityBools to check if the NOT_VISIBLE return status is met.- `Changed WhatAmIHolding() to return the SimObjPhysics ItemInHand
- Changed variables or functions from
Scripts/PhysicsSceneManager
:- Added
virtual
to functions:Generate_UniqueID
- Added
Scripts/SimObjPhysics
:- Added properties:
shape
- Changed the
Start
function topublic
so we can call it from our scripts - Added
ApplyRelativeForce
to apply force in a direction relative to the agent's current position. - In
FindMySpawnPoints
, ignore receptacle trigger boxes of stacking receptacles that are currently positioned higher than the receptacle itself (in case the receptacle is rotated). - Added
IsSeesaw
property. It locks the XZ position - YZ rotation of the rigidbody and ignores collisions with the agents ground collider. For seesaw pivot points, enableIsSeesaw
and set that object tokinematic
so it ignores agent ground collider collisions while not moving - Added
ApplyTorque
method to apply a torque force to an object - Added
ApplyRotation
method to apply a rotation transformation to an object - Added
ApplyMovement
method to apply a movement transformation to an object - Added
associatedWithAgent
property signifying that this object is held by a simulation agent and interacting with that agent will present this object to the performer - Added
IsLid
property to denote that this object is separate lid from its base container and should be merged after placement - Added
hiddenAndHeldBySimulationAgent
property signifying that this object is held by a simulation agent and not currently visible. This will change to false after interacting with that agent and they present the now visible object to the performer
- Added properties:
Scripts/SimObjType
:- Added
IgnoreType
to theSimObjType
enum,ReturnAllPoints
, andAlwaysPlaceUpright
- Added
Stacking
to theSimObjSecondaryProperty
enum.
- Added
Scripts/StructureObject
:- In
Start
, ignore collisions of the agent and the structure. - Added
AddPlatformLips
method to add configurable lips to all four sides of a structural platform
- In
Scripts/MachineCommonSenseController
:- Added custom
RotateLook
to use relative inputs instead of absolute values. - Added checks to see whether objects exist and set lastActionStatus appropriately for
PutObject
- Added custom
ThrowObject
in order to use a relative directional vector to throw object towards. - Changed 'CheckIfAgentCanMove' to take a reference to a directionMagnitude instead of a copy parameter, so if distance to object is greater than zero, we can move a partial distance in 'moveInDirection' by adjusting the Vector3
- If
PushObject
orPullObject
is called on a held object,ThrowObject
will be called instead of throwing an error. - Update ReceptacleObjects if needed in
PickupObject
.
- Added custom
Scripts/UtilityFunctions
:- Ignore checking collisions on ReceptacleTriggerBoxes in
isObjectColliding
- Ignore checking collisions on ReceptacleTriggerBoxes in
ImageSynthesis/ImageSynthesis
:- Added a null check in
OnSceneChange
- Changed to always use the
Hidden/Depth
Shader - Added property
guidForColors
and way to update it (UpdateGuidForColors
). This is used to create random colors for object masks inOnSceneChange
- Added a null check in
ImageSynthesis/Shaders/Depth
:- Changed the
frag
function to return pixels based on the camera's far clipping pane
- Changed the
- Soccer ball prefab from Ahmet Gencoglu: https://assetstore.unity.com/packages/3d/low-polygon-soccer-ball-84382
- Lava material from LowlyPoly: https://assetstore.unity.com/packages/2d/textures-materials/nature/stylized-lava-texture-153161
This material is based upon work supported by the Defense Advanced Research Projects Agency (DARPA) and Naval Information Warfare Center, Pacific (NIWC Pacific) under Contract No. N6600119C4030. Any opinions, findings and conclusions or recommendations expressed in this material are those of the author(s) and do not necessarily reflect the views of the DARPA or NIWC Pacific.