.. centered:: **iMSTK-Unity**

.. centered:: *User Documentation*

Introduction
============

This document describes the iMSTK-Unity interface as well as how to build and develop it.

Overview
-----------------------

iMSTK is a free & open source C++ toolkit for prototyping interactive multi-modal surgical simulations. The iMSTK-Unity asset provides classes that allow the use of iMSTK features inside of unity, those are amongst others various rigid and deformable models, collision detection and response, geometric importers and filters.

The iMSTK-Unity classes utilizes a C# interface of iMSTK that is generated by using the `SWIG <https://www.swig.org/>`_ tool. This interface is wrapped around most C++ functions and forwards its calls to the original C++ code. This allows you to use iMSTK in C# almost the same way as you would in C++.

   .. figure:: media/ImstkUnityArchitecture1.png
    :width: 600
    :alt: Alternative text
    :align: center

Limitations
-----------------------

Not all iMSTK classes are currently accessible through the Unity layer. Additionally there may be some combinations that have not been tested. Some errors *may* cause Unity to crash, save early and save often. Please report issues you encounter in the iMSTK-Unity `issue tracker <https://gitlab.kitware.com/iMSTK/imstk-unity/-/issues>`_

While there is an OpenHaptics asset available on the `Unity Asset Store <https://assetstore.unity.com/packages/tools/integration/haptics-direct-for-unity-v1-197034>`_. This is currently unsupported by the iMSTK Unity Asset. If you need support for the 3D-Touch series of devices you will have to build iMSTK with the appropriate settings.

Avoid calling ``new Imstk.<ImstkClass>()`` as variable initializers when declaring member variables, initialize in the constructor or later instead e.g.::
	
	// PREFER 
	class Example {
		Imstk.LineMesh mesh;
		
		void Example () {
			mesh = new Imstk.LineMesh();
		}
	}
	
	// AVOID
	class Example {
		Imstk.LineMesh mesh = new Imstk.LineMesh();
	}
	
When initializing in the member declaration you may see unexpected crashes in the binary player under windows.

Project Structure
-----------------------
The files of the asset are split in the following directories: 

   - **Scripts**: This directory is for the runtime scripts of the plugin.
  
   - **Scripts/Editor**: This directory is for the editor scripts of the plugin. These scripts implement custom editor functionality. Editor scripts may use runtime scripts but won't be included in the player, which means you should not use functions from these in your own scripts 

   - **Resources**: This directory contains resources required during runtime.

   - **Editor/Resources**: This directory contains resources required in the editor (such as style sheets or UI markup).

   - **Plugins**: This directory is for libraries (dlls/so) that Unity needs to load.

Directories needed for the project but not relevant to the plugin:

   - **Models, Materials, & Textures**: These directories are for various assets used by the Demo. They are not part of the plugin.

The asset on the store may not contain the latest version of iMSTK-Unity, if you want to be up to date you can check out the sources `from gitlab <https://gitlab.kitware.com/iMSTK/imstk-unity>`_. As the binary files for iMSTK aren't included in the repository, you will also have to build iMSTK yourself when you go this route.

.. _SetupForDevelopment:

Setup for Development
=====================

When checking out iMSTK-Unity from gitlab you will first need to build iMSTK. iMSTK uses CMake for its build system. iMSTK is a superbuild meaning it builds, includes, and links to all of its dependencies. There is no need to go find them. The correct version of iMSTK is included in the repository under `iMSTKSource~` as a git submodule. To make sure it's up to date after an update of the repository run `git submodule update`. To build iMSTK you will need to use `cmake`. When building make sure that the build directory (where the binaries end up) is not inside the `iMSTKSource~` directory but close to the root of you drive, e.g. `C:\imstk-build`, the iMSTK project structure is deep enough that there are issues with windows path length. Additionally turn on the ``IMSTK_BUILD_FOR_UNITY`` cmake switch, This will reduce the number of dependencies that are being built. It will also enable the generation of ".cs" files as well as ".dlls"/".so" files in your install directory that are needed by the ".cs" code. These will be used in Unity. Optionally enable ``iMSTK_USE_VRPN`` and/or ``iMSTK_USE_OpenHaptics`` for device support.

You can install the binaries two different ways, for both methods you need to know the directory in which iMSTK was installed. If you didn't change anything that directory will be called `install` and resides inside the directory that you defined in cmake to build imstk, e.g. ``C:\Projects\imstk\build\install`` : 

- Using ```ImstkSource~\InstallImstk.bat``` the format is 
    ``ImstkSource~\InstallImstk.bat <path to imstk/install>``

- Alternatively you can enable `Developer Mode` for iMSTK inside of Unity. This option ca be found in "Edit->Project Settings->iMSTK Settings". When turned on, you will be prompted to install iMSTK whenever you start Unity. After turning on this option, you may need to restart Unity. When it prompts you, select yes and provide your iMSTK install directory, located in ```<iMSTK build directory>/install```. All the necessary files will be copied. If you don't want to be asked to reinstall iMSTK toggle this option off again.

If you make changes in iMSTK you must reinstall it to Unity.

Note: There is a 'Force Install' button to install iMSTK into Unity at the instant it is clicked. This may not always work depending on if an iMSTK script (that utilizes a given dll) has run in the editor. In that case those dll's cannot be unloaded from Unity.

Note: Make sure Unity is not running, even though closed it may be running in the background and prevent any installation.

Devices
=======

The asset available from the asset store does not have `OpenHaptics <https://support.3dsystems.com/s/article/OpenHaptics-for-Windows-Developer-Edition-v35?language=en_US>`_ or `VRPN <https://github.com/vrpn/vrpn>`_ enabled. To use external devices you will have to build iMSTK. When building, enable 
``iMSTK_USE_VRPN`` or ``iMSTK_USE_OpenHaptics`` respectively. This will create a version of iMSTK with device support enabled. When the build is done install iMSTK into the Unity Asset as described above. 

Debugging
---------

Debugging may be done in visual studio, even on the native side. You must attach the debugger to Unity as you would to any external process. With iMSTK open in visual studio, click debug->attach to process. Select the Unity executable and make sure you're set on native debugging.

