spine-unity Runtime Documentation

Licensing

Integrating an official Spine Runtime into your applications requires a valid Spine license, though you are welcome to use the Spine Runtimes for evaluation purposes.

Getting Started

Installation

To use the spine-unity runtime in your Unity project:

  1. Download and install Unity.
  2. Create a new empty project in the Unity Editor.
  3. Download the latest spine-unity unitypackage. Alternatively you can get the latest changes via Git as described below.
  4. Import the unitypackage (you can double-click on it and Unity will open it).

Getting latest changes via Git instead of the unitypackage

  1. Clone the spine-runtimes Git repository.
  2. Copy the contents of spine-runtimes/spine-unity/Assets/ to your project's Assets/ folder.
  3. Copy the folder spine-runtimes/spine-csharp/src to your project's Assets/Spine/Runtime/spine-csharp folder.

Enabling Compatibility with 2D Toolkit

spine-unity supports 2D Toolkit and can render Spine skeletons using TK2D's texture atlas system. To enable 2D Toolkit compatibility, open Unity's Preferences via Edit -> Preferences... and in section Spine select Define TK2D - Enable.

Optional - Installing Extension UPM Packages

The spine-unity runtime works without additional plugins. Some optional features, such as Timeline or Lightweight Render Pipeline support, are provided via separate Unity Package Manager (UPM) extension packages.

  1. Download the desired Unity Package Manager (UPM) package from the download page or find it in the spine-runtimes/spine-unity/Modules subdirectory on the git repository.
  2. If you have your Unity project open, it is recommended to either a) close Unity or b) close any scene containing Spine components (e.g. by opening a new empty scene).
  3. You can then either unzip (or copy if using git) the package to a) the Packages directory in your project where it will automatically be loaded, or b) to an arbitrary directory outside the Assets directory and then open Package Manager in Unity, select the + icon, choose Add package from disk.. and point it to the package.json file.
  4. The Project panel should now show an entry for your package, e.g. Spine Lightweight RP Shaders under Packages. If the directory is not yet listed, you need to close and re-open Unity to have it display the directory and its contents.

Samples

To explore the spine-unity runtime example scenes:

  1. Download and install Unity.
  2. Create a new empty project in the Unity Editor.
  3. Download the latest spine-unity unitypackage. Alternatively you can get the latest changes via Git as described below.
  4. Import the unitypackage (you can double-click on it and Unity will open it).
  5. Open the project in the Unity Editor, then checkout the different example scenes in the Spine Examples/Getting Started folder in the Project panel. Each example scene has text instructions on how to run it and a description of what you see.

Getting latest changes via Git instead of the unitypackage

  1. Clone the spine-runtimes Git repository.
  2. Copy the contents of spine-runtimes/spine-unity/Assets/ to your project's Assets/ folder.
  3. Copy the folder spine-runtimes/spine-csharp/src to your project's Assets/Spine/Runtime/spine-csharp folder.

You can inspect and modify the C# code of both the samples and the spine-unity runtime by opening the project in Unity Editor and selecting Assets -> Open C# Project. For additional information on the example scenes, please see section Example Scenes.

Updating Your Project's spine-unity Runtime

Before updating your project' spine-unity runtime, please consult our guide on Spine editor and runtime version management.

Note: Json and binary skeleton data files exported from Spine 3.7 or earlier will not be readable by the spine-unity 3.8 runtime! The skeleton data files need to be re-exported using Spine 3.8.

If you have many projects, we suggest automating exporting your project files as described here.
For example, we use this script to export all the Spine example projects and to create texture atlases: export.sh

Please consult the following upgrade guides when updating from spine-unity 3.6 or 3.7 to newer versions:

It is recommended to perform the following steps to prevent potential problems:

  1. As with Unity updates, it is always recommended that you back up your whole Unity project before performing an update.
  2. Always check with your Lead Programmer and Technical Artist before updating your Spine runtime. Spine runtimes are source-available and designed to be user-modifiable based on varying project needs. Your project's Spine runtime may have been modified by your programmer. In this case, updating to the latest runtime also requires reapplying those modifications to the new version of the runtime.
  3. Read the CHANGELOG.md file included in the downloaded unitypackage or on github. You can find the necessary documentation here when obsolete methods have been replaced with new counterparts.

Once you are sure you want to update to the latest spine-unity runtime:

  1. Get the latest spine-unity runtime by downloading the latest spine-unity unitypackage. Alternatively you can update by pulling the latest changes from the spine-runtimes Git repository via Git as described below.
  2. Close the Unity Editor and Visual Studio/Xcode.
  3. When upgrading to a different major or minor version (e.g. from 3.7 to 3.8), delete the previous spine-unity installation directories Assets/Spine and Assets/Spine Examples from your project.
  4. Open the project in the Unity Editor. In case you removed the previous spine-unity installation, ignore any logged errors.
  5. Import the unitypackage (you can double-click on it and Unity will open it).

Getting latest changes via Git instead of the unitypackage

  1. Get the latest spine-unity runtime by pulling the latest changes from the spine-runtimes Git repository.
  2. When upgrading to a different major or minor version (e.g. from 3.7 to 3.8), delete the previous spine-unity installation directories Assets/Spine and Assets/Spine Examples from your project.
  3. Copy the contents of spine-runtimes/spine-unity/Assets/ to your project's Assets/ folder.
  4. Copy the folder spine-runtimes/spine-csharp/src to your project's Assets/Spine/Runtime/spine-csharp folder.

Note: The spine-unity runtime is based on the generic spine-csharp runtime. Make sure to watch changes to both the spine-unity and spine-csharp runtime on GitHub.

Updating an Extension UPM Package

When upgrading an optional extension UPM package:

  • The same principles as updating the Spine Unity runtime apply.
  • As mentioned above, it is always recommended that you back up your whole Unity project before performing an update.

In-place Update (via .zip file or git)

  1. If you have your Unity project open, it is recommended to either a) close Unity or b) close any scene containing Spine components (e.g. by opening a new empty scene).
  2. Copy the content of the new UPM package zip file or git directory over the existing one. Depending on how you have installed the UPM package, this will be either the project_root/Packages/package_name directory in your project or the arbitrary directory outside the Assets directory from where you have loaded it via Add package from disk...
  3. If you have closed Unity, open your project again in Unity.
  4. Unity will import the new assets and display a loading progress bar.

Scripting in Unity

If you are not familiar with programming in C# and using Unity in general, we recommend watching the official Unity Tutorials first. The Interface Essentials and then Scripting topics are a good place to start. Note that the Animation topic is not directly applicable to spine-unity since Spine provides its own animation workflow.

Using the spine-unity Runtime

Overview

The spine-unity runtime is a Unity plugin supporting playback and manipulation of animations created with Spine. The spine-unity runtime is written in C# and based on the generic spine-csharp runtime. The spine-unity runtime wraps the spine-csharp structs and functions and exposes them as Unity components. Additionally, the spine-unity runtime imports files exported from the Spine Editor and stores them in custom Unity asset types.

Please consult the Spine Runtimes Guide for a detailed overview of the Spine Runtime architecture.

Asset Management

Exporting Spine Assets for Unity

Export User Guide

You can find complete instructions in the Spine User Guide on how to

  1. Export skeleton & animation data
  2. Export texture atlases containing the images of your skeleton

Spine Unity Export for Beginners

The following shows a simple way to export Spine assets for Unity.

  1. After you have created your skeleton and animations, click on Spine Menu>Export... (CTRL+E). This opens the Export window.

  2. Choose JSON on the upper-left of the Export window.

  3. Check the Create atlas checkbox. (Checking Nonessential data, Pretty print are also recommended for beginners).

    1. Click on Settings beside the Create atlas checkbox. This opens the Texture Packer Settings window.
    2. On the lower-right, look for the textbox labeled Atlas extension and make sure it is set to .atlas.txt.
    3. You're done with the Texture Packer Settings window. Click OK to close.
  4. In the Export window, pick an output folder. (Recommendation: Create a new empty folder.)

  5. Click Export.

  6. This will export three files:

    1. skeleton-name.json or skeleton-name.skel.bytes, containing your skeleton and animation data.
    2. skeleton-name.atlas.txt, containing information about the texture atlas.
    3. One or more .png files, each representing on page of your texture atlas containing the packed images your skeleton uses.

Note: For 2D Toolkit users, Step 3 (packing a .png and .atlas.txt) is not necessary. Instead, you will have the appropriate field in your SkeletonDataAsset to assign a reference to tk2dSpriteCollectionData. Please consult the Installation section of this page on how to enable 2D Toolkit support.

Advanced - Export for SkeletonGraphic

Due to limitations of the used Unity CanvasRenderer, SkeletonGraphic is limited to a single texture. This means Skeletons used in UI have to be packed as a single-texture (single-page) atlas, rather than multi-page atlases.

If they do not fit into a single atlas page, you can pack texture atlas pages grouped by folder. This way you can ensure that each skin requires only a single atlas page and thus can be used with SkeletonGraphic.

When the images are placed in the respective folders, you can export the skeleton with the following steps:

  1. Press Ctrl+E or in the dropdown menu select Export...
  2. Enable Texture Atlas Pack and select Image Folder instead of Attachments right to it.
  3. (optional) Check in Pack Settings if under Options in the bottom right Flatten Paths and Combine Subdirectories is disabled (this is the default).
  4. Click Export.

Advanced - Premultiplied vs Straight Alpha Export

Spine offers two basic workflows via Texture Packer Settings how atlas textures can be exported:

  1. Premultiplied alpha (the default, premultiplied in Gamma color space)
  2. Straight alpha

Premultiplied alpha workflow offers some advantages over straight alpha, no additional draw calls for additive-blended attachments and better mip-map generation being two of them.

It is very important to match export and import settings correctly, see section Advanced - Premultiplied vs Straight Alpha Import for correct settings in Unity.

Importing Spine Assets into Unity

  1. Open your Unity project in the Unity Editor. It should already have a functioning spine-unity runtime in it, as described in section Installation.
  2. Open the folder of the exported files. (.json, .atlas.txt and .png)
  3. Copy the exported files (or the folder containing them) to your desired subfolder of your project's Assets folder. You can do this by dragging the exported files from an Explorer/Finder window into your desired folder in Unity's Project panel.

The spine-unity runtime will automatically generate the necessary additional Unity assets upon detecting the added files.

The following assets are generated:

  1. an _Atlas asset for the texture atlas file (.atlas.txt). It holds a reference to the material and the .atlas.txt file.
  2. a _Material asset for each texture atlas page (.png). It holds references to the shader and the .png texture.
  3. a _SkeletonData asset for skeleton data files (.json, .skel.bytes). It holds a reference to the .json or .skel.bytes file and the generated _Atlas asset. It additionally provides custom import and animation settings for your skeleton, see section Skeleton Data Asset.

Advanced - Premultiplied vs Straight Alpha Import

As described in Advanced - Premultiplied vs Straight Alpha Export, Spine offers two basic workflows of how atlas textures can be exported:

  1. Premultiplied alpha (the default, premultiplied in Gamma color space)
  2. Straight alpha

Important Note: It is very important that whenever the Premultiply alpha setting is enabled upon atlas texture export, both the Material's Straight Alpha Texture parameter and the Texture's Alpha Is Transparency setting in Unity are disabled and vice versa.

Whenever you see dark borders around transparent areas, or colorful stripes around your attachment images, it is very likely because of incorrect import settings.

Correct Texture Packer export and Texture and Material import settings:
  1. Premultiplied Alpha Texture Packer setting Premultiply alpha enabled,
    Unity Texture settings sRGB (Color Texture) enabled and Alpha Is Transparency disabled,
    Unity Material parameter Straight Alpha Texture disabled.

  2. Straight Alpha Texture Packer setting Premultiply alpha disabled, Bleed enabled,
    Unity Texture settings sRGB (Color Texture) enabled and Alpha Is Transparency enabled,
    Unity Material parameter Straight Alpha Texture enabled.

The default texture packer settings use Premultiply alpha. All Spine shaders that come with the spine-unity runtime are also configured to use Premultiply alpha workflow by default, they have the Straight Alpha Texture parameter disabled as default.

There might are use cases however, where you may want to use straight alpha workflow. Some of the use cases are:

  1. When using Linear color space, you must use straight alpha.
    The premultiplication is performed in Gamma space upon export, which will cause incorrect borders when converted back to Linear space on import. You will receive a log warning message when this combination is detected at a material.
  2. When you want to use a shader other than the included Spine shaders.
    Typically shaders will assume straight alpha textures, which will lead to incorrect black borders around attachment images.

Be sure to configure all textures and materials accordingly as described above when switching to straight alpha workflow. You can check or modify the current color space via Project Settings - Player - Other Settings - Color Space.

Updating Spine Assets

During development, you may frequently update your Spine skeleton data and texture atlas files. You can simply overwrite these files (.json, .skel.bytes, .atlas.txt, .png). Re-export the assets from the Spine Editor and copy the exported files to your subfolder of your project's Assets folder again, overwriting the existing files.

Unity will detect changes to these files and automatically re-import the modified assets. After re-import, all references to previously imported Spine assets will be intact and use the latest data.

Note: Unity sometimes fails to recognize file changes. In this case, locate the folder containing the Spine assets in Unity's Project panel that you want to re-import, right-click on the folder, then select Reimport from the context menu.

Skeleton Data Asset

The skeleton data asset (named with suffix _SkeletonData) stores information about the bone hierarchy, slots, draw order, animations and other data that constitutes your skeleton. Other components provided by the spine-unity runtime reference and share this skeleton data asset to animate and display a skeleton.

To inspect or modify a skeleton data asset, select it in Unity's Project panel. The Inspector panel will display all properties of the skeleton data for review and modification.

Skeleton Data

The SkeletonData section provides general import settings of the skeleton.

Scale allows you to specify a custom import scale value, affecting all skeleton instances referencing this data asset. Changing the value will immediately affect all instances of this skeleton.

SkeletonData Modifiers provide a way for users to add additional processing to skeleton data assets after loading from a .json or .skel.bytes file has been completed. Please consult section SkeletonData Modifier Assets below for additional information.

Atlas

Atlas references are used by the skeleton to resolve the exported image name references to the respective image areas for rendering.

Upon import the Atlas Assets array is automatically populated with one entry per atlas asset (ending with _Atlas).

In case spine-unity failed to automatically assign all required atlas assets, you can change the Atlas Assets Size to the desired amount of atlas assets and manually assign the required atlas assets to Element0 - ElementN.

Mix Settings

The skeleton data asset allows you to specify animation mix times.

Default Mix Duration allows you to enter the default mix time, in seconds.

You can define mix times for two specific animations by clicking the Add Custom Mix button in the Custom Mix Durations section of the asset and setting specific mix durations, overriding the default mix duration value above.

Components using the skeleton data asset, like the skeleton animation component, use these mix times when playing back animations.

Preview

The Preview section for a skeleton data asset allows you to inspect all bones, slots, animations, skins, and events contained in the asset.

You can playback animations via the play buttons to the left of each animation and view a live update of the respective slots via Show Attachments in the Slots section. The timeline bar shows all events as purple markers. Hover over the markers while playing to display the event name.

Use the Create Animation Reference Assets button to generate reference assets for all animations of the skeleton. An AnimationReferenceAsset acts as a Unity asset referencing a single Spine.Animation and can be assigned to component properties in the Inspector.

Skeleton Mecanim

In case you want to use Unity's Mecanim animation system instead of Spine's default animation system, you can generate and assign a Mecanim controller via Generate Mecanim Controller.

Texture Atlas Asset

The texture atlas asset contains information about the images used by your skeleton, namely on what texture atlas page an image is stored, as well as its UV texture coordinates on the texture atlas page.

You can view the material of the texture atlas pages by double clicking the material asset in the Materials array.

Note: You can modify the materials and textures referenced by the texture atlas asset. When modifying textures, make sure the UV texture coordinates stay valid.

The Set Mipmap Bias to -0.5 button is intended for advanced users and can be used to compensate for blurry appearance when Generate Mip Maps is enabled on an atlas texture.

You can generate sprites for each image element of an atlas by pressing the Apply Regions as Texture Sprite Slices button. The generated sprites reference areas of the texture atlas image (png file) and can be used as any Unity sprite asset.

SkeletonData Modifier Assets

SkeletonData modifier assets provide a way for users to add additional processing to skeleton data assets after loading from a .json or .skel.bytes file has been completed.

SkeletonDataAsset's Inspector provides a Skeleton Data Modifiers list you can add assets to.

Included SkeletonData Modifiers - BlendModeMaterialsAsset

BlendModeMaterialsAsset is a SkeletonData modifier asset class included in spine-unity. It holds references to materials that can be used to render attachments within slots that have the Additive, Multiply and Screen blend modes assigned to them in the Spine editor.

The Material references stored in BlendModeMaterials assets are used as templates to generate new Materials that use the appropriate texture needed by the loaded attachments.

The spine-unity runtime comes packaged with a ready-to-use BlendModeMaterialsAsset named Default BlendModeMaterials. Using this included asset allows the attachments in slots with special blend modes to use the included default Multiply and Screen shaders: Spine/Blend Modes/Skeleton PMA Multiply and Spine/Blend Modes/Skeleton PMA Screen.

If you need to use different Materials or shaders or Materials with different settings, you can create new BlendModeMaterialsAssets using Create -> Spine -> SkeletonData Modifiers -> Blend Mode Materials. Then assign your Material templates to the created asset.

Writing a custom SkeletonDataModifierAsset class

You can write your own custom SkeletonDataModifierAsset class to add additional processing to skeleton data assets after loading from a .json or .skel.bytes file. SkeletonDataModifierAsset is an abstract ScriptableObject class where you can derive your own classes from.

  1. Create a new class derived from SkeletonDataModifierAsset and implement the void Apply (SkeletonData skeletonData) method. Add the CreateAssetMenu class attribute to list an entry for your class in the Asset -> Create menu.

    [[CreateAssetMenu(menuName = "TopMenu/Submenu/SubSubmenu", order = 200)]
    public class BlendModeMaterialsAsset : SkeletonDataModifierAsset {

    public override void Apply (SkeletonData skeletonData) {
        ...
    }
    }
  2. Create an instance of your new class by selecting your desired folder in the Project panel and selecting your newly created Asset -> Create menu entry. Assign the created asset at an element of the Skeleton Data Modifiers list of your SkeletonData asset.

Apply(skeletonData) will be called after loading data from the .json or .skel.bytes file has been completed.

Main Components

The spine-unity runtime provides you with a set of components that allow to display, animate, follow and modify skeletons exported from Spine. These components reference skeleton data and texture atlas assets you import as described above.

Adding a Skeleton to a Scene

To quickly display a Spine skeleton in your Unity project:

  1. Import the skeleton data and texture atlas as described above.
  2. Drag the _SkeletonData asset into the Scene view or the Hierarchy panel and choose SkeletonAnimation. A new GameObject will be instantiated, with the required Spine components already set up.

Note: Alternatively to step 2, you can create the same GameObject from scratch:

  1. Create a new empty GameObject via GameObject -> Create Empty.
  2. Select the GameObject and in the inspector click Add Component, then select SkeletonAnimation. This will automatically add the additional MeshRenderer and MeshFilter components as well.
  3. At the SkeletonAnimation component, assign the Skeleton Data Asset property by dragging the desired _SkeletonData asset into it.

Note: In case you only see bones of a skeleton in Scene view without any images attached, you might want to switch the Initial Skin property to a skin other than default.

You can now use the components' C# API to animate the skeleton, react to events triggered by animations, etc. Refer to the component documentation below for more details.

Alternatives to SkeletonAnimation - SkeletonGraphic (UI) and SkeletonMecanim

Instantiating a skeleton as SkeletonAnimation is the recommended way to use a Spine skeleton in Unity, as it provides the most complete feature set of the three alternatives.

The three alternatives to instantiate a skeleton are:

  1. SkeletonAnimation - Uses Spine's custom animation and event system, providing highest customizability. Renders using a MeshRenderer, interacting with masks such as SpriteMask like a Unity sprite. The recommended way of using a Spine skeleton in Unity.
  2. SkeletonGraphic (UI) - For use as UI element together with a Unity Canvas. Renders and interacts with UI masks such as RectMask2D like the built-in Unity UI elements. Animation and event behaviour is identical to SkeletonAnimation.
  3. SkeletonMecanim - Uses Unity's Mecanim animation and event system for starting, mixing and transitioning between animations. Provides fewer animation mixing and transition options than SkeletonAnimation. When using SkeletonMecanim it will not be guaranteed that transitions will look as previewed in the Spine Editor.

SkeletonAnimation Component

The SkeletonAnimation component is one of three ways to use a Spine skeleton in Unity. These alternatives are: SkeletonAnimation, SkeletonMecanim and SkeletonGraphic (UI).

The SkeletonAnimation component is the heart of the spine-unity runtime. It allows you to add a Spine skeleton to a GameObject, animate it, react to animation events, and so on.

Setting Skeleton Data

A SkeletonAnimation component requires a reference to a skeleton data asset from which it can get the information about a skeleton's bone hierarchy, slots etc.

If you have added a skeleton to a scene via drag and drop, the skeleton data asset is automatically assigned. In case you have an already set up GameObject and suddenly want to change the skeleton to a different asset, you can manually change it via the provided Inspector property.

To set or change the skeleton data

  1. Select the SkeletonAnimation GameObject
  2. Assign a _SkeletonData asset at the SkeletonData Asset property in the Inspector.

Setting Initial Skin and Animation

The SkeletonAnimation Inspector exposes the following parameters

  1. Initial Skin. This skin will be assigned upon start. Note: In case you only see bones of a skeleton without any images attached, you might want to switch to a skin other than default to show your skin.
  2. Animation Name. This animation will be played upon start.
  3. Loop. Defines whether the initial animation shall be looped or played only once.
  4. Time Scale. You can set the time scale to slow down or speed up playback of animations.

Setting Advanced Parameters

Unfold the Advanced section in the SkeletonAnimation Inspector to show advanced configuration parameters.

The SkeletonAnimation Inspector exposes the following advanced parameters

  • Initial Flip X, Initial Flip Y. These parameters allow you to flip the skeleton horizontally and vertically upon start. This will set ScaleX and ScaleY to -1 where flipped.
  • Use single submesh. Can be enabled to simplify submesh generation by assuming you are only using one Material and need only one submesh. This is will disable multiple materials, render separation, and custom slot materials.
  • Immutable triangles. Can be enabled to optimize rendering for skeletons that never change attachment visbility. If true, triangles will not be updated. Enable this as an optimization if the skeleton does not make use of attachment swapping or hiding, or draw order keys. Otherwise, setting this to false may cause errors in rendering.
  • Clear State on Disable. Clears the state of the render and skeleton when this component or its GameObject is disabled. This prevents previous state from being retained when it is enabled again. When pooling your skeleton, setting this to true can be helpful.
  • Separator Slot Names. Slots that determine where the render is split. This is used by components such as SkeletonRenderSeparator so that the skeleton can be rendered by two separate renderers on different GameObjects.
  • Z-Spacing. Attachments are rendered back to front in the x/y plane by the skeleton renderer component. Each attachment is offset by a customizable z-spacing value on the z-axis to avoid z-fighting.

  • PMA Vertex Colors. Multiply vertex color RGB with vertex color alpha. Set this to true if the shader used for rendering is configured to use premultiplied alpha (parameter Straight Alpha Texture disabled). Setting this to false disables single-batch additive slots and may increase the number of draw calls.
  • Tint Black (!). Adds black tint vertex data to the mesh. Black tinting requires that the shader interpret UV2 and UV3 as black tint colors for this effect to work. You may use the included Spine/Skeleton Tint Black shader. If you only need to tint the whole skeleton and not individual parts, the Spine/Skeleton Tint shader is recommended for better efficiency and changing/animating the _Black material property via MaterialPropertyBlock. See section Shaders for additional information.
  • Add Normals. When enabled, the mesh generator adds normals to the output mesh. Enable if your shader requires vertex normals. For better performance and reduced memory usage, you can instead use a shader such as the Spine/Skeleton Lit shader that assumes the desired normal. Note that the Spine/Sprite shaders can be configured to assume a Fixed Normal as well.
  • Solve Tangents. Some lit shaders require vertex tangents, usually for applying normal maps. When enabled, tangents are calculated every frame and added to the output mesh.
  • Add Skeleton Utility. This button can be used to quickly add a SkeletonUtility component to the GameObject for tracking or overriding bone positions. See SkeletonUtility for further info.
  • Debug. Sometimes you may want to know the current color of a slot or scale of a bone while the game is running. Pressing the Debug button opens the Skeleton Debug window which was created for this purpose. It allows you to inspect the current state of bones, slots, constraints, draw order, events and statistical information about your skeleton.

Life-cycle


In the SkeletonAnimation component, AnimationState holds the state of all currently playing and queued animations. Every Update, the AnimationState is updated so that the animations progress forward in time. And then the new frame is applied to the Skeleton as a new pose.

Your scripts may run before or after SkeletonAnimation's Update. If your code takes Skeleton or bone values before SkeletonAnimation's Update, your code will read values from the previous frame instead of the current one.

The component exposes the event callback delegates as properties that allow you to intercept this life-cycle before and after the world transforms of all bones are calculated. You can bind to these delegates to modify bone positions and other aspects of the skeleton without having to care for the update order of your actors and components.

SkeletonAnimation Update Callbacks

  • SkeletonAnimation.UpdateLocal is raised after the animations for the frame is updated and applied to the skeleton's local values. Use this if you need to read or modify bone local values.
  • SkeletonAnimation.UpdateComplete is raised after world values are calculated for all bones in the Skeleton. SkeletonAnimation makes no further operations in Update after this. Use this if you only need to read bone world values. Those values may still change if any of your scripts modify them after SkeletonAnimation's Update.
  • SkeletonAnimation.UpdateWorld is raised after the world values are calculated for all the bones in the Skeleton. If you subscribe to this event, it will call skeleton.UpdateWorldTransform a second time. Depending on the complexity of your skeleton or what you are doing, this may be unnecessary, or wasteful. Use this event if you need to modify bone local values based on bone world values. This is useful for implementing custom constraints in Unity code.

As an alternative, you can change Script Execution Order to run after SkeletonAnimation's Update method.

For more information on Unity's MonoBehaviour Lifecycle, see: docs.unity3d.com/Manual/ExecutionOrder

C#

Interacting with a skeleton via code requires accessing the SkeletonAnimation component. As applies to Unity components in general, it is recommended to query the reference once and store it for further use.

...
using Spine.Unity;

public class YourComponent : MonoBehaviour {

   SkeletonAnimation skeletonAnimation;
   Spine.AnimationState animationState;
   Skeleton skeleton;

   void Awake () {
      skeletonAnimation = GetComponent<SkeletonAnimation>();
      animationState = skeletonAnimation.AnimationState;
      skeleton = skeletonAnimation.Skeleton;
   }

Skeleton

The SkeletonAnimation component provides access to the underlying skeleton via the SkeletonAnimation.Skeleton property. A Skeleton stores a reference to a skeleton data asset, which in turn references one or more atlas assets.

The Skeleton allows you to set skins, attachments, reset bones to setup pose and scale and flip the whole skeleton.

Setting Attachments

To set an attachment, provide the slot and attachment name.

C#
bool success = skeletonAnimation.Skeleton.SetAttachment("slotName", "attachmentName");

Resetting to Setup Pose

For procedural animation it is sometimes necessary to reset bones and/or slots to their setup pose.

C#
skeleton.SetToSetupPose();
skeleton.SetBonesToSetupPose();
skeleton.SetSlotsToSetupPose();

Setting Skins

A Spine skeleton may have multiple skins that define which attachment go on which slot. The skeleton component provides a simple way to switch between skins.

C#
bool success = skeletonAnimation.Skeleton.SetSkin("skinName");

Combining Skins

Spine skins can be combined to e.g. form a complete character skin from single cloth item skins. See the new Skin API documentation for more details.

C#
var skeleton = skeletonAnimation.Skeleton;
var skeletonData = skeleton.data;
var mixAndMatchSkin = new Skin("custom-girl");
mixAndMatchSkin.AddSkin(skeletonData.FindSkin("skin-base"));
mixAndMatchSkin.AddSkin(skeletonData.FindSkin("nose/short"));
mixAndMatchSkin.AddSkin(skeletonData.FindSkin("eyelids/girly"));
mixAndMatchSkin.AddSkin(skeletonData.FindSkin("eyes/violet"));
mixAndMatchSkin.AddSkin(skeletonData.FindSkin("hair/brown"));
mixAndMatchSkin.AddSkin(skeletonData.FindSkin("clothes/hoodie-orange"));
mixAndMatchSkin.AddSkin(skeletonData.FindSkin("legs/pants-jeans"));
mixAndMatchSkin.AddSkin(skeletonData.FindSkin("accessories/bag"));
mixAndMatchSkin.AddSkin(skeletonData.FindSkin("accessories/hat-red-yellow"));
skeleton.SetSkin(mixAndMatchSkin);
skeleton.SetSlotsToSetupPose();
Runtime Repacking

While combining skins, multiple materials may be accumulated. This leads to additional draw calls. The Skin.GetRepackedSkin() method can be used to combine used texture regions of a collected skin to a single texture at runtime.

using Spine.Unity.AttachmentTools;

// Create a repacked skin.
Skin repackedSkin = collectedSkin.GetRepackedSkin("Repacked skin", skeletonAnimation.SkeletonDataAsset.atlasAssets[0].PrimaryMaterial, out runtimeMaterial, out runtimeAtlas);
collectedSkin.Clear();

// Use the repacked skin.
skeletonAnimation.Skeleton.Skin = repackedSkin;
skeletonAnimation.Skeleton.SetSlotsToSetupPose();
skeletonAnimation.AnimationState.Apply(skeletonAnimation.Skeleton);

// You can optionally clear the cache after multiple repack operations.
AtlasUtilities.ClearCache();

Note: Depending on platform capabilities, you may need to set the Read/Write Enabled parameter at sprite textures that shall be combined to a repacked texture.

You can examine the example scenes Spine Examples/Other Examples/Mix and Match and Spine Examples/Other Examples/Mix and Match Equip and the used MixAndMatch.cs example script for further insights.

Changing Scale and Flipping a Skeleton

Flipping a skeleton vertically or horizontally allows you to reuse animations, e.g. a walk animation facing left can be played back to face right.

C#
bool isFlippedX = skeleton.ScaleX < 0;
skeleton.ScaleX = -1;
bool isFlippedY = skeleton.ScaleY < 0;
skeleton.ScaleY = -1;

skeleton.ScaleX = -skeleton.ScaleX; // toggle flip x state

Getting and Setting Bone Transforms Manually

Note: Recommended for very special use cases only. The Spine BoneFollower and Spine SkeletonUtilityBone components are an easier way to interact with bones.

The Skeleton lets you set and get bone transform values so you can implement IK terrain following or let other actors and components such as particle systems follow the bones in your skeleton.

Note: Make sure you apply new bone positions as part of the update world transform life-cycle, otherwise your modifications may be overwritten by animations.

C#
Bone bone = skeletonAnimation.skeleton.FindBone("boneName");
Vector3 worldPosition = bone.GetWorldPosition(skeletonAnimation.transform);

Vector3 position = ...;
bone.SetPositionSkeletonSpace(position);

Quaternion worldRotationQuaternion = bone.GetQuaternion();

Controlling Animation - AnimationState

Life-cycle

The SkeletonAnimation component implements the Update method in which it updates the underlying AnimationState based on the delta time, applies the AnimationState to the skeleton, and updates the world transforms of all bones of the skeleton.

The skeleton animation component exposes the AnimationState API via the SkeletonAnimation.AnimationState property. This section assumes a familiarity with concepts like tracks, track entries, mix times, or animation queuing as described in the section Applying Animations in the generic Spine Runtime Guide.

Time Scale

You can set the time scale of the skeleton animation component to slow down or speed up the playback of animations. The delta time used to advance animations is simply multiplied with the time scale, e.g. a time scale of 0.5 slows the animation down to half the normal speed, a time scale of 2 speeds it up to twice the normal speed.

C#
float timeScale = skeletonAnimation.timeScale;
skeletonAnimation.timeScale = 0.5f;

Setting Animations

To set an animation, provide the track index, animation name and whether to loop the animation.

C#
TrackEntry entry = skeletonAnimation.AnimationState.SetAnimation(trackIndex, "walk", true);
Queueing Animations

To queue an animation, provide the track index, animation name, whether to loop the animation, and the delay after which this animation should start playing on the track in seconds.

C#
TrackEntry entry = skeletonAnimation.AnimationState.AddAnimation(trackIndex, "run", true, 2);

Setting and Queueing Empty Animations, Clearing Tracks

The skeleton animation component also provides methods to set an empty animation, queue an empty animation, or clear one or all tracks. All of these work analogous to the methods and nodes shown above.

C#
TrackEntry entry = skeletonAnimation.AnimationState.SetEmptyAnimation(trackIndex, mixDuration);
entry = skeletonAnimation.AnimationState.AddEmptyAnimation(trackIndex, mixDuration, delay);
skeletonAnimation.AnimationState.ClearTrack(trackIndex);
skeletonAnimation.AnimationState.ClearTracks();

Track Entries

You'll receive a TrackEntry from all the methods that allows you to further customize the playback of this specific animation, as well as bind to delegates of track entry specific events. See the section Processing AnimationState Events below.

Note: The returned track entries will only be valid until the corresponding animation is removed from the underlying animation state. The Unity garbage collector will automatically free them. After a dipose event is received for a track entry, it should no longer be stored or accessed.

C#
TrackEntry entry = ...
entry.EventThreshold = 2;
float trackEnd = entry.TrackEnd;

Processing AnimationState Events

While animations are played back by the underlying AnimationState, various events will be emitted that notify listeners that

  1. An animation started.
  2. An animation was interrupted, e.g. by clearing a track or setting a new animation.
  3. An animation was completed without interruption, which may occur multiple times if looped.
  4. An animation has ended.
  5. An animation and its corresponding TrackEntry have been disposed.
  6. A user defined event was fired.

Note: When setting a new animation which interrupts a previous one, no complete event will be raised but interrupt and end events will be raised instead.

The skeleton animation component provides delegates to which C# code can bind in order to react to these events for all queued animations on all tracks. Listeners can also be bound to the corresponding delegates of a specific TrackEntry only.

C#

In the class that should react to AnimationState events, add delegates for the events you want to listen to:

SkeletonAnimation skeletonAnimation;
Spine.AnimationState animationState;

void Awake () {
   skeletonAnimation = GetComponent<SkeletonAnimation>();
   animationState = skeletonAnimation.AnimationState;

   animationState.Start += OnSpineAnimationStart;
   animationState.Interrupt += OnSpineAnimationInterrupt;
   animationState.End += OnSpineAnimationEnd;
   animationState.Dispose += OnSpineAnimationDispose;
   animationState.Complete += OnSpineAnimationComplete;

   animationState.Event += OnUserDefinedEvent;
}

public void OnSpineAnimationStart(TrackEntry trackEntry) {
   // Add your implementation code here to react to start events
}
public void OnSpineAnimationInterrupt(TrackEntry trackEntry) {
   // Add your implementation code here to react to interrupt events
}
public void OnSpineAnimationEnd(TrackEntry trackEntry) {
   // Add your implementation code here to react to end events
}
public void OnSpineAnimationDispose(TrackEntry trackEntry) {
   // Add your implementation code here to react to dispose events
}
public void OnSpineAnimationComplete(TrackEntry trackEntry) {
   // Add your implementation code here to react to complete events
}

public void OnUserDefinedEvent(Spine.TrackEntry trackEntry, Spine.Event e) {
   // Add your implementation code here to react to user defined event
}

See the Spine API Reference for detailled information.

Coroutine Yield Instructions

The spine-unity runtime provides a set of yield instructions for use with Unity's Coroutines. If you are new to Unity Coroutines, the Coroutine tutorials and Coroutine documentation are a good place to start.

The following yield instructions are provided:

  1. WaitForSpineAnimation. Waits until a Spine.TrackEntry raises one of the specified events.

    var track = skeletonAnimation.state.SetAnimation(0, "interruptible", false);
    var completeOrEnd = WaitForSpineAnimation.AnimationEventTypes.Complete |
                         WaitForSpineAnimation.AnimationEventTypes.End;
    yield return new WaitForSpineAnimation(track, completeOrEnd);
  2. WaitForSpineAnimationComplete. Waits until a Spine.TrackEntry raises a Complete event.

    var track = skeletonAnimation.state.SetAnimation(0, "talk", false);
    yield return new WaitForSpineAnimationComplete(track);
  3. WaitForSpineAnimationEnd. Waits until a Spine.TrackEntry raises an End event.

    var track = skeletonAnimation.state.SetAnimation(0, "talk", false);
    yield return new WaitForSpineAnimationEnd(track);
  4. WaitForSpineEvent. Waits until a Spine.AnimationState raises a user-defined Spine.Event (named in Spine editor).

    yield return new WaitForSpineEvent(skeletonAnimation.state, "spawn bullet");
    // You can also pass a Spine.Event's Spine.EventData reference.
    Spine.EventData spawnBulletEvent; // cached in e.g. Start()
    ..
    yield return new WaitForSpineEvent(skeletonAnimation.state, spawnBulletEvent);

Note: Like Unity's built-in yield instructions, instances of these spine-unity yield instructions can be reused to prevent additional memory allocations.

Tutorial Page

You can find a tutorial page on spine-unity events here.

SkeletonMecanim Component

The SkeletonMecanim component is one of three ways to use a Spine skeleton in Unity. These alternatives are: SkeletonAnimation, SkeletonMecanim and SkeletonGraphic (UI).

The SkeletonMecanim component is an alternative to the SkeletonAnimation component, using Unity's Mecanim animation system instead of the Spine animation system. As the SkeletonAnimation component, it allows you to add a Spine skeleton to a GameObject, animate it, react to animation events, and so on.

It provides similar parameters as the SkeletonAnimation component, please consult the SkeletonAnimation section for additional information.
The SkeletonMecanim Inspector exposes the following additional parameters:

  • Translator
    • Auto Reset. When set to true, the skeleton state is mixed out to setup pose when an animation finishes, according to the previous animation's keyed items.
    • Layer Mix Modes. This parameter determines the animation mix mode at each layer. You can change it from SpineStyle to Always Mix or Mix Next to get behaviour more related to usual Mecanim transitions, respecting Mecanim transition weights. When set to SpineStyle it will be more consistent with Spine Editor preview or SkeletonAnimation behaviour, and it will ignore Mecanim transition weights.

The SkeletonMecanim component uses the Controller asset assigned at the Animator component as usual with Unity Mecanim. The Controller asset is automatically generated and assigned when instantiating a skeleton as SkeletonMecanim via drag and drop.

You can add animations to the Controller's animation state machine via drag and drop of Spine animations to the Animator panel as usual. The animations can be found below the Controller asset.

Note: currently rootmotion is not yet supported at SkeletonMecanim. It is planned to be implemented in future updates.

SkeletonMecanim Events

When using SkeletonMecanim, events are stored in each AnimationClip and are raised like other Unity animation events. For example, if you named your event "Footstep" in Spine, you need to provide a MonoBehaviour on your SkeletonMecanim GameObject with a method named Footstep() to handle it. When using folders in Spine, the method name will be a concatenation of the folder name and the animation name. For example when the previous event is placed in a folder named Foldername it will be FoldernameFootstep().

For more information on Unity Mecanim events, see Unity's Documentation on Animation Events.

SkeletonGraphic Component

The SkeletonGraphic component is one of three ways to use a Spine skeleton in Unity. These alternatives are: SkeletonAnimation, SkeletonMecanim and SkeletonGraphic (UI).

The SkeletonGraphic component is an alternative to the SkeletonAnimation component, using Unity's UI system for layout, rendering and mask interaction. As the SkeletonAnimation component, it allows you to add a Spine skeleton to a GameObject, animate it, react to animation events, and so on.

Important Note: due to limitations of the used Unity CanvasRenderer, SkeletonGraphic is limited to a single texture. This means Skeletons used in UI have to be packed as a single-texture (single-page) atlas, rather than multi-page atlases. See section Advanced - Export for SkeletonGraphic for a possible workarounds to this limitation.

It provides similar parameters as the SkeletonAnimation component, please consult the SkeletonAnimation section for additional information.
The SkeletonGraphic Inspector exposes the following additional parameters:

  • Unscaled Time. When set to true, updates will be performed according to Time.unscaledDeltaTime instead of Time.deltaTime. This is useful to animated UI elements independently of slow-motion effects.
  • Freeze. When set to true, the SkeletonGraphic will no longer be updated.

Tip: You can make a SkeletonGraphic's RectTransform fit its current pose’s dimensions by right-clicking the SkeletonGraphic component in the inspector and selecting Match RectTransform with Mesh Bounds from the context menu.

Tutorial Page

You can find a tutorial page on SkeletonGraphic here.

SkeletonRenderer Component

The SkeletonRenderer component is responsible for drawing the current state of a skeleton. It is the base class for SkeletonAnimation and SkeletonMecanim.

Note: most of the time you will want to use SkeletonAnimation, SkeletonMecanim or SkeletonGraphic (UI) instead. These components provide sophisticated means to control animation. Only when applying animations manually without transitions, as could be useful at a UI gauge element, this component may be useful as-is.

Rendering is performed via a procedural mesh which is updated at a MeshRenderer component. The component uses the texture atlas asset referenced by the SkeletonDataAsset to find the textures and materials needed to draw the attachments of the skeleton. Please consult the documentation section of SkeletonAnimation for additional information.

You can examine the example scene Spine Examples/Other Examples/SpineGauge on how to use a SkeletonRenderer component directly.

Utility Components

BoneFollower

This component references a bone of a SkeletonAnimation component and sets its own transform to that of the bone on every Update.

Note: There is a BoneFollowerGraphic component provided for SkeletonGraphic objects.

In contrast to the SkeletonUtilityBone component a BoneFollower can be used as a single isolated GameObject without any parent bone objects.

Use this to let objects like particle systems follow a specific bone on the skeleton.

You can examine the example scene Spine Examples/Getting Started/4 Object Oriented Sample on how to set up a BoneFollower component.

BoneFollowerGraphic

This component is a variant of the Bone Follower component to be used with SkeletonGraphic components.

In contrast to the SkeletonUtilityBone component a BoneFollowerGraphic can be used as a single isolated GameObject without any parent bone objects.

Use this to let objects like particle systems follow a specific bone on the skeleton.

You can examine the example scene Spine Examples/Getting Started/6 Skeleton Graphic on how to set up a BoneFollowerGraphic component.

PointFollower

This component is similar to the Bone Follower component but follows a PointAttachment instead of a bone.

In contrast to the SkeletonUtilityBone component a PointFollower can be used as a single isolated GameObject without any parent bone objects.

BoundingBoxFollower

This component is used to match a Bounding Box at a skeleton's slot. It extracts the shape and assign it at a PolygonCollider2D and enables or disables it every frame to match the current animation.

Note: the bone's position is not automatically followed, which is why it is typically used together with a BoneFollower component. You can use the Add Bone Follower button in the BoundingBoxFollower inspector to create and setup a BoneFollower component.

See Bone Follower for further information.

SkeletonUtilityBone

Sometimes you may want to modify bone positions programmatically at runtime to react to physics or user input.

The SkeletonUtilityBone component provides a convenient interface to let GameObjects follow a bone position, override a bone position manually or via 2D and 3D physics. It can be configured to either follow the local bone position or override it on every Update. When set to Override, the component will set the bone position before the SkeletonAnimation component updates the world transforms.

Important Note: A SkeletonUtilityBone uses local transform values. It relies on a hierarchy of SkeletonUtilityBone GameObjects that mirrors the skeleton's bone hierarchy. The recommended way to quickly create a SkeletonUtilityBone hierarchy is via the SkeletonUtility component described below.

The SkeletonUtilityBone Inspector also provides an interface to create additional child bones (selectively or recursively) or create a 2D and 3D hinge chain.

Once your hierarchy of SkeletonUtilityBones is created, the Hierarchy panel shows different icons next to a SkeletonUtilityBone GameObject depending on whether it is set to

  • Follow: Follow
  • or Override: Override

Example Use Case

Use a SkeletonUtilityBone in Override mode for use cases such as letting the user drag a bone of the skeleton around.

In case you need a GameObject to follow only a single bone position, you can use the BoneFollower component instead to save resources.

Example Scene

You can find an example scene that demonstrates usage of SkeletonUtilityBone at Spine Examples/Other Examples/SkeletonUtility Animated Physics. It shows how some SkeletonUtilityBones nodes are configured to Follow bone positions to be the necessary hierarchial parents for the Override nodes.

SkeletonUtility

Creating a Hierarchy of SkeletonUtilityBones

The SkeletonUtility component offers a quick way to create a hierarchy of SkeletonUtilityBone GameObjects mirroring the bone hierarchy of the skeleton.

To create a SkeletonUtility component, select your SkeletonAnimation component and in the Inspector unfold the Advanced section and hit Add Skeleton Utility. Once created, the Add Skeleton Utility button will disappear and SkeletonUtility component is added to your GameObject.

The SkeletonUtility component provides a Spawn Hierarchy button with the following options presented on click:

  1. Follow all bones Creates SkeletonUtilityBone GameObjects for all bones in the hierarchy, set to mode Follow
  2. Follow (Root Only) Creates only the root SkeletonUtilityBone GameObject, set to mode Follow
  3. Override all bones Creates SkeletonUtilityBone GameObjects for all bones in the hierarchy, set to mode Override
  4. Override (Root Only) Creates only the root SkeletonUtilityBone GameObject, set to mode Override

EachSkeletonUtilityBone can then be configured to override bone positions of a skeleton where necessary.

Note: You can add additional SkeletonUtilityBone GameObjects via the inspector of a SkeletonUtilityBone later, the Spawn Hierarchy functionality serves as a rough starting point. You can also delete unneeded SkeletonUtilityBone GameObjects to save resources. Just remember you need to keep their parents intact, so do not delete GameObjects in the middle of a hierarchy-chain or change their parents.

SkeletonUtilityConstraint

C#

Base class to derive skeleton utility constraint subclasses from. It automatically registers itself at the parent SkeletonUtility and will be updated accordingly.

See example constraint classes SkeletonUtilityGroundConstraint and SkeletonUtilityEyeConstraint for how to write your own constraint classes.

Example Scenes

The spine-unity runtime comes with example scenes that demonstrate the above constraints. You can find them in Spine Examples/Other Examples/SkeletonUtility GroundConstraint and Spine Examples/Other Examples/SkeletonUtility Eyes.

SkeletonRendererCustomMaterials

You may want to override materials for a specific Skeleton instance or even only at certain slots. This component provides an inspector interface to assign custom material overrides for SkeletonRenderer, including subclasses SkeletonAnimation and SkeletonMecanim.

You can right-click on a SkeletonRenderer (or subclasses SkeletonAnimation and SkeletonMecanim) and select Add Basic Serialized Custom Materials to add this component to the renderer. Add entries to the Custom Slot Materials array to override materials at certain slots or to the Custom Material Overrides array to replace one material with another for the whole skeleton. Be sure to uncheck Override Disabled to enable the respective material overrides.

Note: This component is not intended to be interfaced through code. To dynamically set materials for your SkeletonRenderer through code, you can directly access SkeletonRenderer.CustomMaterialOverride for material array overrides and SkeletonRenderer.CustomSlotMaterials for slot material overrides.

SkeletonRenderSeparator and SkeletonPartsRenderer

You may want to display other GameObjects between parts of your character, e.g. to let your character run into a tree and display one leg in front and one behind the trunk. The SkeletonRenderSeparator component allows you to split your SkeletonRenderer (or subclass SkeletonAnimation and SkeletonMecanim) into two or more SkeletonPartsRenderers with customizable layer order.

Note: Normally, Spine renderer components will use a single renderer to display the whole mesh of a skeleton. This unfortunately prevents you from inserting other UnityEngine.Renderers (SpriteRenderer, MeshRenderer, ParticleSystem, etc.) between its parts.

Setup

  1. Make sure you know your Skeleton's draw order. Find out which slot you want to use to separate your Skeleton's render into parts. For convenience, label this slot clearly before exporting your Skeleton.

  2. Add the SkeletonRenderSeparator component Select your Spine GameObject. Right-click on your SkeletonAnimation or SkeletonRenderer in the inspector. Choose Add Skeleton Render Separator. This will add the SkeletonRenderSeparator component to the GameObject.

"Steps 2 to 4"

  1. Assign Separator Slots The inspector now shows a warning that the list of separators is empty. Setup separator slots by choosing the desired slot(s) under Separator Slot Names. You can add additional separator slots using the + button.

    Note: This field is serialized at the SkeletonRenderer (or SkeletonAnimation and SkeletonMecanim subclass) component, SkeletonRenderSeparator just provides the interface for it.

  2. Add Parts Renderers The inspector now shows a warning that you don't have enough parts renderers.
    Click on the Add the missing renderers (n) button to create the required GameObjects with SkeletonPartsRenderer components. These GameObjects will be automatically assigned at the Parts Renderers list above.

    Note: The SkeletonRenderSeparator detects the currently required number of parts renderers,depending on the current draw order. If draw order is modified at runtime, it may happen that the renderer requires more parts renderers. In this case you may need to add one or two additional parts renderers manually by clicking the Add Parts Renderer button.

  3. Setup Sorting Layer and Order in Layer Each of the SkeletonPartsRenderers provides a Sorting Layer and Order in Layer property in the inspector. You can now setup the sorting properties at each SkeletonPartsRenderer. Higher values will move the renderer to the front.

Note: The SkeletonPartsRenderer GameObjects don't have to be children of your Spine GameObject. The SkeletonRenderSeparator keeps references, so you can organize them however you need to.

Example Scene

You can find an example scene that demonstrates usage of SkeletonPartsRenderer and SkeletonRenderSeparator at Spine Examples/Other Examples/SkeletonRenderSeparator.

C#

Enabling and Disabling

By default, SkeletonRenderSeparator will disable the SkeletonRenderer and take over his mesh rendering task. Likewise, if you disable SkeletonRenderSeparator, SkeletonRenderer will take over rendering again.

You can enable and disable a SkeletonRenderSeparator as any component:

skeletonRenderSeparator.enabled = true; // separation is enabled.
skeletonRenderSeparator.enabled = false; // separation is disabled.
Changing the separation point

The point of separation is not stored in SkeletonRenderSeparator.
It is defined by the separator slots in SkeletonRenderer (or subclasses SkeletonAnimation and SkeletonMecanim). If you want to manipulate separator slots at runtime, you can access the list SkeletonRenderer.separatorSlots and manipulate it as usual by calling Add, Remove or Clear.

Spine.Slot mySlot = skeletonAnimation.Skeleton.FindSlot("MY SPECIAL SLOT");
skeletonAnimation.separatorSlots.Clear();
skeletonAnimation.separatorSlots.Add(mySlot);
Adding a SkeletonRenderSeparator at runtime

You can use the static method SkeletonRenderSeparator.AddToSkeletonRenderer to add and initialize a new SkeletonRenderSeparator component.

SkeletonAnimation skeletonAnimation = GetComponent<SkeletonAnimation>();
skeletonAnimation.SeparatorSlots.Add(mySlot); // see above

// Add the SkeletonRenderSeparator.
SkeletonRenderSeparator skeletonRenderSeparator = SkeletonRenderSeparator.AddToSkeletonRenderer(skeletonAnimation);

By default, it will add the currently necessary SkeletonPartsRenderers. It provides a number of optional arguments for advanced use cases, please see the code documentation.

Rendering

Shaders

The spine-unity runtime includes several different shaders. By default, the Spine/Skeleton shader will be assigned at a newly imported skeleton Material. You can change the shader via the Material's Shader parameter as usual. Below you will find a list of included Spine shaders.

  1. Spine/Skeleton (Default Shader).

    Unlit transparent shader. Does not write to the z-buffer.

  2. Spine/Skeleton Graphic (Default shader for SkeletonGraphic)

    Unlit transparent shader used by SkeletonGraphic. Does not write to the z-buffer. Limited to a single texture because of CanvasRenderer limitations.

  3. Spine/Skeleton Lit.

    Simple lit transparent shader, no normal map support. Does not write to the z-buffer.

  4. Spine/Skeleton Lit ZWrite.

    Simple lit transparent shader, no normal map support. Writes to the z-buffer.

  5. Spine/Skeleton Fill.

    Unlit transparent shader with customizable color overlay. Does not write to the z-buffer.
    FillColor determines the overlay color, FillPhase the color overlay intensity.

  6. Spine/Skeleton Tint.

    Unlit transparent shader with customizable two-color tint, tinting dark colors separately from light colors, called tint black. Does not write to the z-buffer.

    The texture's lighter colors are tinted with Tint Color, the texture's darker colors with Black Point color. This allows a tinted texture to be brighter than its original color, compared to ordinary multiply color blending. When setting both Tint Color and Black Point to the same color it will result in a solid color overlay. When setting Tint Color to white and Black Point to black, the texture color will be inverted.

  7. Spine/Skeleton Tint Black

    Unlit transparent shader with Spine-animated per-slot tint black feature. Does not write to the z-buffer.

    Spine provides a Tint Black feature for slots, allowing animated black tint.

    Required additional setup step (for tint color vertex data):

  8. Spine/Skeleton Tint Black Additive

    Unlit transparent shader with Spine-animated per-slot tint black feature. Uses additive blend mode. Does not write to the z-buffer.

  9. Spine/SkeletonGraphic Tint Black

    Variant of Spine/Skeleton Tint Black shader for SkeletonGraphic.

    Required additional setup steps (for tint color vertex data):

    1. Enable Tint Black in the SkeletonAnimation's inspector in the Advanced section.
    2. Set the Material of the SkeletonGraphic to the SkeletonGraphicTintBlack material located in folder Spine/Runtime/spine-unity/Materials.
    3. Select the parent Canvas and under Additional Shader Channels enable TexCoord1 and TexCoord2.
  10. Spine/Sprite

    Sophisticated configurable shaders, allowing for more advanced lighting than the Spine/Skeleton Lit shader. You can find a demonstration of the Spine/Sprite/Vertex Lit shader in the example scene Spine Examples/Other Examples/Sprite Shaders.

    1. Spine/Sprite/Unlit
      Unlit shader with configurable blend mode, overlay color, hue, saturation and brightness adjustments. Configurable to write to z-buffer. Fog support.
    2. Spine/Sprite/Vertex Lit
      Sophisticated vertex-lit shader with configurable blend mode.
      Supports normal maps, secondary albedo, metallic and emission maps.
      Configurable color ramp for cel-shaded look and rim lighting based on normals.
      Configurable overlay color, hue, saturation and brightness adjustments.
      Configurable to write to z-buffer. Fog support.
    3. Spine/Sprite/Pixel Lit
      Pixel-lit variant of Spine/Sprite/Vertex Lit shader.
  11. Spine/Special
    1. Spine/Special/Skeleton Grayscale

      Unlit transparent shader for grayscale rendering with customizable intensity. Does not write to the z-buffer.

    2. Spine/Special/Skeleton Ghost

      Special shader used by SkeletonGhost component for trail rendering.

  12. Spine/Blend Modes

    Intended for slots that have blend modes Additive, Multiply and Screen assigned in the Spine editor. It is recommended to automatically assign blend mode materials on import via the provided BlendModeMaterials SkeletonData Modifier asset.

    1. Spine/Blend Modes/Skeleton PMA Additive Unlit transparent shader. Uses additive blend mode. Does not write to the z-buffer.
    2. Spine/Blend Modes/Skeleton PMA Multiply Unlit transparent shader. Uses multiply blend mode. Does not write to the z-buffer.
    3. Spine/Blend Modes/Skeleton PMA Screen Unlit transparent shader. Uses screen blend mode. Does not write to the z-buffer.

Example of the Spine/Tint Black shader.

LWRP Shaders - Extension UPM Package

Lightweight Render Pipeline (LWRP) shaders are provided as a separate UPM (Unity Package Manager) package. See section Optional - Installing Extension UPM Packages on how to download and install this package and section Updating an Extension UPM Package on how to update it.

The LWRP Shaders UPM package provides shaders specifically built for Unity's lightweight render pipeline:

  1. Lightweight Render Pipeline/Spine/Skeleton

    Lightweight variant of the Spine/Skeleton shader.

  2. Lightweight Render Pipeline/Spine/Skeleton Lit

    Lightweight variant of the Spine/Skeleton Lit shader

  3. Lightweight Render Pipeline/Spine/Sprite

    Lightweight variant of the Spine/Sprite/Vertex Lit and Pixel Lit shaders.

The shaders can be assigned to materials as usual and will respect your settings of the assigned LightweightRenderPipelineAsset under Project Settings - Graphics.

You can find a demonstration of the LWRP shaders in the example scene com.esotericsoftware.spine.lwrp-shaders-3.8/Examples/LWRP Shaders.unity in the extracted package.

Materials

The Materials array of a MeshRenderer is managed by the SkeletonRenderer every frame, depending on the currently assigned attachments and the AtlasAssets these are contained in.

Note: Direct modifications to the Materials array have no effect as they will be overwritten in the following frame.

Material Switching and Draw Calls

If assigned attachments are distributed across multiple atlas pages, e.g. material A and material B, the Materials array is set according to the draw order in which the materials are needed.

If the order is:

  1. Attachment from A
  2. Attachment from A
  3. Attachment from B
  4. Attachment from A

The resulting material array will be:

  1. Material A (for attachments 1 and 2)
  2. Material B (for attachment 3)
  3. Material A (for attachment 4)

Every material in the Materials array corresponds to a draw call. Therefore a high ammount of material switching adversely affects performance.

The Dragon example shows an unfortunate use case with many draw calls:

It is therefore recommended to pack attachments to as few atlas pages as possible, and to group attachments to atlas pages according to draw order to prevent unnecessary material switching. Please see Spine Texture Packer: Folder Structure on how to arrange atlas regions in your Spine atlases.

Changing Materials Per Instance

Note: Direct modifications to the SkeletonRenderer's Materials array have no effect as they will be overwritten in the following frame.

CustomMaterialOverride and CustomSlotMaterial

SkeletonRenderer allows you to override Materials on specific slots or override the resulting materials.

To replace an original material with your new material at runtime for an instance of SkeletonRenderer, you can use SkeletonRenderer.CustomMaterialOverride:

C#
skeletonAnimation.CustomMaterialOverride[originalMaterial] = newMaterial; // to enable the replacement.
skeletonAnimation.CustomMaterialOverride.Remove(originalMaterial); // to disable that replacement.

To use a replacement Material on just a specific slot, you can use SkeletonRenderer.CustomSlotMaterial:

C#
skeletonAnimation.CustomSlotMaterial[slot] = newMaterial; // to enable the replacement.
skeletonAnimation.CustomSlotMaterial.Remove(slot); // to disable that replacement.
MaterialPropertyBlocks

You can use Renderer.SetPropertyBlock to override material property values for a single MeshRenderer.

C#
MaterialPropertyBlock mpb = new MaterialPropertyBlock();
mpb.SetColor("_FillColor", Color.red); // "_FillColor" is a named property on the used shader.
GetComponent<MeshRenderer>().SetPropertyBlock(mpb);

// to deactivate the override again:
MaterialPropertyBlock mpb = this.cachedMaterialPropertyBlock; // assuming you had cached the MaterialPropertyBlock
mpb.Clear();
GetComponent<Renderer>().SetPropertyBlock(mpb);

You can find a demonstration of per-instance material properties in the example scene Spine Examples/Other Examples/Per Instance Material Properties.

Notes on optimization

  • Using Renderer.SetPropertyBlock allows renderers with the same material to be batched correctly even if their material properties are changed by different MaterialPropertyBlocks.
  • You need to call SetPropertyBlock whenever you change or add a property value to your MaterialPropertyBlock. But you can keep that MaterialPropertyBlock as part of your class so you don't have to keep instantiating a new one whenever you want to change a property.
  • When you need to set a property frequently, you can use the static method: Shader.PropertyToID(string) to cache the int ID of that property instead of using the string overload of MaterialPropertyBlock's setters.

Transparency and Draw Order

All spine-unity shaders use alpha blending to cleanly draw semi-transparent transitions at borders of attachments. Without alpha blending (using a hard transparency threshold) hard jagged outlines would be the result, similar to aliasing artifacts.

Unfortunately, alpha blending presents classical problems as the z-buffer cannot be used for automatic depth sorting. Instead, triangles need to be rendered in back-to-front order, painting parts over each other. Each SkeletonRenderer generates it's mesh accordingly, with triangles following the Slot draw order defined in Spine. Within a single mesh, even a single draw call will paint correctly ordered skeleton parts.

Between meshes, spine-unity utilizes many of Unity’s render order systems to determine what mesh should be on top of which. Using the standard spine-unity setup, whole skeleton meshes are rendered in an order determined by multiple factors:

  1. Camera depth. Relevent in multi-camera setups.
  2. Material.renderQueue. When set, it overrides the shader's Queue tag.
  3. Shader's Queue tag. Defaults to "Transparent" queue in Spine shaders as other sprites.
  4. Sorting Group components. When placed on the MeshRenderer's GameObject or on any of the parents GameObjects.
  5. Renderer's SortingLayer and SortingOrder within a layer.
  6. Distance from the camera. Cameras can be configured whether planar or perspective distance is used.

If a scene's renderers are in the same sorting layer and order and the shader Queue tags are equal, you can control sorting of your Spine GameObjects via distance to the camera. Note that cameras provide a transparencySortMode property.

Sorting Layer and Order in Layer

The inspector of a SkeletonRenderer (or subclasses SkeletonAnimation and SkeletonMecanim) provides Sorting Layer and Order in Layer properties which actually modify the MeshRenderer's sortingLayerID and sortingOrder properties. These properties are stored as part of MeshRenderer and are not part of SkeletonRenderer.

You can access these properties via code:

C#
GetComponent<MeshRenderer>().sortingOrder = 1; // Change the Order in Layer to 1.

Preventing Incorrect Sorting

Especially when using an orthographic camera, it may occur that skeletons using multiple atlas pages are sorted incorrectly. You can counter this by adding a Sorting Group component to the skeleton GameObject. Another workaround is to rotate the camera by a tiny ammount, e.g. set the camera's transform rotation Y value to 0.001.

Rendering Objects between Parts of a Skeleton

You may want to display other GameObjects between parts of your character, e.g. to let your character run into a tree and display one leg in front and one behind the trunk.

spine-unity provides a SkeletonRenderSeparator component for the purpose of splitting a skeleton into multiple parts.

Fading a Skeleton In or Out

Unfortunately, alpha blending will cause back parts of your skeleton show through when lowering the alpha value of your skeleton to make it semi-transparent. This is a common problem due to transparency being applied when each triangle is drawn.

One solution to this problem is to use a temporary RenderTexture. You can render the whole character to the RenderTexture at normal opacity and then draw the content of this RenderTexture to your scene at the desired fade opacity.

Note that this is only one of many ways to achive a fade-out effect. There may be other easier solutions such as gradually tinting the skeleton with a solid color, decreasing scale, etc. Existing 2D games may serve as valuable inspiration, as RenderTextures are a costly solution that has rarely been used in the past.

Example Components

spine-unity comes with additional example components that demonstrate solutions for some advanced use cases. The most important example components are listed below.

SkeletonRagdoll and SkeletonRagdoll2D

You may want to turn an animated skeleton into a puppet-like ragdoll, e.g. to simulate falling down via physics in case of death. This can be achieved with the SkeletonRagdoll and SkeletonRagdoll2D example components, which provide a comfortable interface to create ragdoll physics components at a SkeletonRenderer (or subclasses SkeletonAnimation and SkeletonMecanim).

You can find a demonstration of the SkeletonRagdoll2D component in the example scene Spine Examples/Other Examples/SkeletonUtility Ragdoll.

SkeletonGhost

You may want to render a motion-trail or motion-blur effect at at character to simulate speed or power. The SkeletonGhost example component can be attached at a SkeletonRenderer (or subclasses SkeletonAnimation and SkeletonMecanim) to draw the skeleton multiple times, using a customizable material.

SkeletonUtilityKinematicShadow

You may want to have some bones to receive some inertia or to react to movement of other bones. This may be useful to have a cape follow the movement of a character in a more convincing way. This can be achieved with the SkeletonUtilityKinematicShadow component. It allows hinge chains to inherit a velocity interpreted from changes in parent transform position or from unrelated rigidbodies.

You can find a demonstration of the SkeletonUtilityKinematicShadow component in the example scene Spine Examples/Other Examples/SkeletonUtility Animated Physics.

Example Scenes

The spine-unity runtime includes example scenes to demonstrate the most important components and usage of the C# API for common use cases. You can find them in the Spine Examples top level directory. Each scene includes a description text that will help you to quickly discover and understand the relevant parts.

If you are using the spine-unity runtime for the first time, it is highly recommended to check out at least the example scenes in the Spine Examples/Getting Started.

Spine Examples / Getting Started

The example scenes in the Spine Examples/Getting Started demonstrate the fundamental components and basic use cases.

1 The Spine GameObject

This scene demonstrates the SkeletonAnimation component and the referenced SkeletonDataAsset which provides the necessary data.

2 Controlling Animation

This scene demonstrates basic animation code using the C# API - starting animations and reacting to animation events.

When pressing play, Spineboy will sequentially play animations walk, run, idle, and turn. Footstep events will trigger a sound accordingly.

You can inspect the example script SpineBeginnerTwo component which is attached at the spineboy GameObject. It demonstrates usage of SkeletonAnimation.AnimationState.SetAnimation() and SkeletonAnimation.AnimationState.AddAnimation(). The script HandleEventWithAudioExample attached at the sound GameObject shows how you can hook up your own event method callback by registering it at SkeletonAnimation.AnimationState.Event.

3 Controlling Animation Continued

This scene demonstrates how you can play animations simultaneously by using multiple animation tracks. It also shows how to use AnimationReferenceAssets as an alternative to using animation name strings.

When pressing play, the walk animation will start to play in a loop. At the same time, and in its own timeframe, the gungrab and gunkeep animations are playing as a secondary animation.

You can inspect the example script Raptor attached at the raptor Skeleton GameObject. It shows how to expose AnimationReferenceAsset properties at a component and assign it as animation by calling the SkeletonAnimation.AnimationState.SetAnimation() method, on tracks 0 and 1.

4 Object Oriented Sample

This scene demonstrates how you can setup a platformer character following the Model-View-Controller object oriented software design pattern. Please note that while this setup might not be the most suitable for your projects, it shall serve as inspiration on how input, game logic and visualization may be separated into components.

When pressing play, you can control the Spineboy character with WASD (move), Spacebar (jump) and mouse input (aim and fire). Alternatively you can control it via an XBOX Controller.

You can inspect the example script SpineboyBeginnerInput attached at the PLAYER INPUT GameObject, acting as controller. It modifies the state of the model represented by the SpineboyBeginnerModel component attached at the PLAYER Spineboy GameObject. Visualization of this state is performed by the SpineboyBeginnerView component, attached at the VIEW Spineboy GameObject, acting as view. It starts the respective animations at the SkeletonAnimation component which is attached at the same GameObject.

5 Basic Platformer

This scene demonstrates the use case of a platformer with typical animations such as jump, run, fall, land, complete with particles and sound effects. It also shows how Spine meshes can be used to cast shadows in Unity.

Note: If you do not see any cast shadows, please enable shadows via Edit - Preferences - Quality - Shadows.

When pressing play, you can control the Hero character with WASD (move) and Spacebar (jump). Alternatively you can control it via an XBOX Controller.

You can inspect the example script BasicPlatformerController attached at the Player GameObject. It shows how you can use Unity input to change between a character's states which are tracked in a newly created CharacterState attribute. When states change, the SkeletonAnimationHandleExample example script is used to transition to the new animation, while the HeroEffectsHandlerExample example script is used to play a sound and spawn particle systems.

6 SkeletonGraphic

This scene demonstrates the SkeletonGraphic component and how it can be integrated into an existing Unity UI. It also shows how BoneFollowerGraphic components can be used to attach text labels to follow bone positions. They can be found at the Detached BoneFollowerGraphic and Child BoneFollowerGraphic GameObjects.

When pressing play, you will see a Canvas-based user interface where Doi and Spineboy are integrated into a scrollable panel. Both play looping animations just as a SkeletonAnimation component while being part of the UI.

Timeline Extension UPM Package

Timeline support is provided as a separate UPM (Unity Package Manager) package. See section Optional - Installing Extension UPM Packages on how to download and install this package and section Updating an Extension UPM Package on how to update it.

Spine-Unity Timeline Playables

Spine Timeline currently provides two types of Timeline Playables: Spine AnimationState Track and Spine Skeleton Flip Track, described below.

Limitations: currently only SkeletonAnimation is supported. You can find an implementation for SkeletonGraphic kindly provided by a forum user on this forum thread.

Spine AnimationState Track


This track type can be used to set animations on the target SkeletonAnimation's AnimationState.

To use:

  1. Add SkeletonAnimationPlayableHandle component to your SkeletonAnimation GameObject.
  2. With an existing Unity Playable Director, and in the Unity Timeline window, right-click on an empty space on the left and choose Spine.Unity.Playables - Spine Animation State Track.
  3. Drag the SkeletonAnimation GameObject onto the empty reference property of the new Spine AnimationState Track.
  4. Right-click on the row in an empty space in the Timeline dopesheet and choose Add Spine Animation State Clip Clip.
  5. Adjust the start and end times of the new clip, name it appropriately at the top of the Inspector.
  6. Click on the clip inspector's SkeletonDataAsset field and choose your target skeleton's SkeletonDataAsset. This will enable the animation name dropdown to appear.
  7. Choose the appropriate animation name, loop, and mix settings.

  • For easier readability, rename your clip to the animation name or something descriptive.
  • To avoid having to do steps 4-6 repeatedly, use the Duplicate function (CTRL/CMD + D)

Track Behavior

  • AnimationState.SetAnimation will be called at the beginning of every clip based on the animationName.
  • Clip durations don't matter. Animations won't be cleared where there is no active clip at certain slices of time.
  • Empty animation: If a clip has no name specified, it will call SetEmptyAnimation instead.
  • Error handling: If the animation with the provided animationName is not found, it will do nothing (the previous animation will continue playing normally).
  • Animations playing before the timeline starts playing will not be interrupted until the first clip starts playing.
  • At the end of the last clip and at the end of the timeline, nothing happens. This means the effect of the last clip's SetAnimation call will persist until you give other commands to that AnimationState.
  • If "custom duration" is unchecked, it will do a normal lookup of the AnimationState data's specified transition-pair mix setting, or the default mix.
  • Edit mode preview mixing may look different from Play Mode mixing. Please check in actual Play Mode to see the real results.

Spine Skeleton Flip Track


This track type can be used to flip the skeleton of the target SkeletonAnimation.

To use:

  1. Add SkeletonAnimationPlayableHandle component to your SkeletonAnimation GameObject.
  2. With an existing Unity Playable Director, and in the Unity Timeline window, right-click on an empty space on the left and choose Spine.Unity.Playables - Spine Skeleton Flip Track.
  3. Drag the SkeletonAnimation GameObject onto the empty reference property of the new Spine Skeleton Flip Track.
  4. Right-click on the row in an empty space in the Timeline dopesheet and choose Add Spine Skeleton Flip Clip Clip.
  5. Adjust the start and end times of the new clip, name it appropriately at the top of the Inspector, and choose the desired FlipX and FlipY values.

Track Behavior

  • The specified skeleton flip values will be applied for every frame within the duration of each track.
  • At the end of the timeline, the track will revert the skeleton flip to the flip values it captures when it starts playing that timeline.

Known Issues

  • The Console potentially logs an incorrect/harmless error DrivenPropertyManager has failed to register property "m_Script" of object "Spine GameObject (spineboy-pro)" with driver "" because the property doesn't exist.. This is a known issue on Unity's end. See more here: https://forum.unity.com/threads/default-playables-text-switcher-track-error.502903/
  • These Spine Tracks (like other custom Unity Timeline Playable types) do not have labels on them. Unity currently doesn't have API to specify their labels yet.
  • Each track clip currently requires you to specify a reference to SkeletonData so its inspector can show you a convenient list of animation names. This is because track clips are agnostic of its track and target component/track binding, and provides no way of automatically finding it while in the editor. The clips will still function correctly without the SkeletonDataAsset references; you just won't get the dropdown of animation names in the editor.
  • Each track clip cannot be automatically named based on the chosen animationName. The Timeline object editors currently doesn't provide access to the clip names to do this automatically.