Library is an interactive diorama I created with some help from Adam Madojemu. I started this project as an excuse to get familiar with Unity's Mecanim animation system.

There was an idea...

The idea seemed fairly straightforward. SEEMED.

I wanted to create an interactive diorama wherein the player could manipulate the state of the world to get an NPC to react. It would be a Unity project targeting WebGL, created in under a month and set in a Library. That's doable, right?

An early sketch of the project.

I wanted the interactions to be simple in isolation but complex when layered, able to make the NPC do certain things if the conditions were right. At the same time I wanted to make the affordances easy enough to intuit that the player wouldn't need a tutorial, and hopefully discover these interactions themselves.

A rudimentary map I put together in Miro.

I initially intended for the player to manipulate the time of day, affecting lighting and weather in realtime. This quickly proved to be out of scope from a technical standpoint, so I opted to have the player manipulate objects instead.

Onto the animations

I knew that animation would be the biggest bottleneck as I'd be creating everything from scratch. To save myself some time, I opted to use assets from a previous project, kitbashing the environment and using a pre-made character for the NPC. The character's design allowed me to avoid authoring complex facial performances, allowing me to focus most of my time on body movements.

Unfortunately the plugin I used for hair sim does not support WebGL so I had to tie the character's hair back for the final build. I ended up with around seven or eight animations in total (which in hindsight is not nearly enough).

I ended up with a total of five interactive objects. The Ipad and Radio proved rather straightforward to animate, all I had to do was increase the emission values to make them glow when activated. The Window proved even easier, it just needed to rotate around its pivot. Where it got tricky was with the Blinds and the Lantern.

A work in progress still.

As much as possible, I wanted the player to be able to see the effect of their interactions on the world by having it visibly change. Following that logic, the Blinds and Lantern needed to have a significant effect on lighting, which was a big ask due to technical constraints. To achieve this, both objects have realtime lights attached to them. The lantern is more overt and affects both the NPC and environment, while the Blinds are more subtle and act as indirect lights, the warm lights blending to cooler tones when activated, changing the atmosphere of the room.

In a bid to keep the file sizes low, I opted not to use any audio in the project. This however, resulted in a couple of interactions and animations needing visual indictors in place of sounds. To fix this, I opted to use VFX. 

Bug Flipbook

There's an interaction where the Lantern attracts bugs, and without sounds, I needed to indicate that to the player. So I created a quick animation in procreate, converted that into a flipbook and used it as part of a particle system. I did the same for the Radio as well as an animation for the NPC. In some cases like the radio, I found it worked quite well and kept with my creative goals.

Implementation

I used Unity's visual scripting to program the interactions. Each of the objects had on/off states, so it was fairly straightforward to set them up. The NPC was a whole other story.

Script for NPC

The NPC was first set up with basic reactions, glancing at or being surprised by whatever object the player clicks on. Each of these glancing animations return to the idle stated after being played so I was able to reuse a lot of the nodes, simply assigning integers to each animation. This worked until I needed more complex states, like the NPC falling asleep.

Up until this point each animation was triggered as direct result of player input, but the sleeping animation will only trigger if the room is completely dark (Lantern off and Blinds closed). To make this possible I had to add an animation event for the NPC that checks the world state so they know when to sleep. This ended up being useful for other interactions like the aforementioned bugs. However, there was another unforseen issue: the players.

It turned out that players press buttons at a much faster rate than i'd anticipated. Most playtesters would flick multiple objects on and off simultaneously which left the NPC struggling to keep up. It was at this point I realised I'd underestimated the number of animations i'd needed to make this NPC believable, but it was too late in the timeline to produce new assets. Instead, I added nodes to manage how busy the NPC was, ignoring incoming player interactions if its already reacting to one. This solution is far from ideal but it at least mitigated the issue.

Screencap of the project in the Unity Editor

Conclusion

I learned a lot on this project, It was my first foray into technical animation and has yielded many insights that I continue to use to this day. Given the chance to do it again, I'd do it very differently. At the same time, I'm quite proud of what I was able to achieve in a relatively short amount of time, and am excited to create more interactive animations.