NavStack
Asynchronous screen transition/navigation for Unity.
com.annulusgames.navstack 
Install via UPM
Add to Unity Package Manager using this URL
https://www.pkglnk.dev/navstack.git?path=src/NavStack/Assets/NavStack README Markdown
Copy this to your project's README.md
## Installation
Add **NavStack** to your Unity project via Package Manager:
1. Open **Window > Package Manager**
2. Click **+** > **Add package from git URL**
3. Enter:
```
https://www.pkglnk.dev/navstack.git?path=src%2FNavStack%2FAssets%2FNavStack
```
[](https://www.pkglnk.dev/pkg/navstack)Dependencies (1)
README
NavStack
Asynchronous screen transition/navigation for Unity.
Overview
NavStack is a library for managing screen transitions in Unity. It provides a foundation interface for asynchronous API-based screen transitions, as well as support for integration with uGUI and content management using Resources/Addressables.
[!NOTE] NavStack is currently released as a preview version. Feedback through issues or pull requests would be appreciated.
Setup
Requirements
- Unity 2021.3 or later
- UniTask 2.0.0 or later
Installation
- Open the Package Manager from Window > Package Manager.
- Click the "+" button > Add package from git URL.
- Enter the following URL:
https://github.com/AnnulusGames/NavStack.git?path=src/NavStack/Assets/NavStack
Alternatively, open Packages/manifest.json and add the following to the dependencies block:
{
"dependencies": {
"com.annulusgames.navstack": "https://github.com/AnnulusGames/NavStack.git?path=src/NavStack/Assets/NavStack"
}
}
Basic Concepts
In NavStack, a screen is divided into units called "Pages." The only requirement for a Page is the implementation of the IPage interface, allowing any object such as GameObjects, VisualElements, or Scenes to be represented as a Page.
Screen transitions and lifecycle management are handled by "Navigation." NavStack provides two types of Navigation: INavigationStack, which can stack Page transitions, and INaviagtionSheet, which switches between active Pages without keeping a history of transitions.
Page Lifecycle
The IPage interface defines the basic events for a Page's lifecycle. Each event is called from the Navigation side, allowing customization of screen transition processes.
public interface IPage
{
UniTask OnNavigatedFrom(NavigationContext context, CancellationToken cancellationToken = default);
UniTask OnNavigatedTo(NavigationContext context, CancellationToken cancellationToken = default);
}
| Event | Description |
|---|---|
| OnNavigatedFrom | Called when navigating away from the Page. |
| OnNavigatedTo | Called when navigating to the Page. |
Additionally, by implementing IPageLifecycleEvent, you can add additional lifecycle events for the Page.
public interface IPageLifecycleEvent
{
UniTask OnAttached(CancellationToken cancellationToken = default);
UniTask OnDetached(CancellationToken cancellationToken = default);
}
NavigationStack
NavigationStack supports stacked screen transitions. Pages pushed onto the stack are stacked, and the last pushed Page becomes the active Page. You can push a Page using PushAsync() and pop using PopAsync().
INavigationStack navigationStack;
IPage page;
await navigationStack.PushAsync(page);
await navigationStack.PopAsync();
You can also add NavigationStack-specific events to Pages by implementing IPageStackEvent.
public interface IPageStackEvent
{
UniTask OnPush(NavigationContext context, CancellationToken cancellationToken = default);
UniTask OnPop(NavigationContext context, CancellationToken cancellationToken = default);
}
NavigationSheet
NavigationSheet supports switching between active Pages, similar to tabs. Unlike NavigationStack, it does not keep a history of Page transitions.
You need to use AddAsync() to add Pages to the NavigationSheet.
INavigationSheet navigationSheet;
IPage page1;
IPage page2;
IPage page3;
await navigationSheet.AddAsync(page1);
await navigationSheet.AddAsync(page2);
await navigationSheet.AddAsync(page3);
To switch the displayed Page, use ShowAsync(). To hide a Page, use HideAsync().
int index = 0;
await navigationSheet.ShowAsync(index);
await navigationSheet.HideAsync();
You can remove Pages using RemoveAsync() or RemoveAllAsync().
await navigationSheet.RemoveAsync(page3);
await navigationSheet.RemoveAllAsync();
NavigationContext
You can pass NavigationContext during Page transitions to pass data between Pages and specify transition options.
Passing Data
You can pass data to the destination Page through NavigationContext.
var page = new ExamplePage();
var context = new NavigationContext()
{
Parameters = { { "id", "123456" } }
};
await navigationStack.PushAsync(page, context, cancellationToken);
class ExamplePage : IPage
{
public UniTask OnNavigatedTo(NavigationContext context, CancellationToken cancellationToken = default)
{
var id = (string)context.Parameters["id"];
...
}
...
}
NavigationOptions
You can specify transition options using NavigationOptions.
var context = new NavigationContext()
{
Options = new NavigationOptions()
{
Animated = true,
AwaitOperation = NavigationAwaitOperation.Drop,
}
};
await navigationStack.PushAsync(page, context, cancellationToken);
| Property | Description |
|---|---|
| Animated | Specifies whether to play transition animations (default is true). |
| AwaitOperation | Specifies the behavior when a transition operation is called again during Page transition (default is NavigationAwaitOperation.Error). |
Workflow for uGUI
When using NavStack with uGUI, add the Navigation Stack / Navigation Sheet component to any object placed under the Canvas.
Next, create Pages for displaying UI. Implement a component that inherits from IPage.
public class SamplePage1 : MonoBehaviour, IPage
{
[SerializeField] CanvasGroup canvasGroup;
public async UniTask OnNavigatedTo(NavigationContext context, CancellationToken cancellationToken = default)
{
if (!context.Options.Animated)
{
canvasGroup.alpha = 1f;
return;
}
// Example implementation using LitMotion for tween animations
await LMotion.Create(0f, 1f, 0.25f)
.WithEase(Ease.InQuad)
.BindToCanvasGroupAlpha(canvasGroup)
.ToUniTask(CancellationTokenSource.CreateLinkedTokenSource(destroyCancellationToken, cancellationToken).Token);
}
public async UniTask OnNavigatedFrom(NavigationContext context, CancellationToken cancellationToken = default)
{
if (!context.Options.Animated)
{
canvasGroup.alpha = 0f;
return;
}
await LMotion.Create(1f, 0f, 0.25f)
.WithEase(Ease.OutQuad)
.BindToCanvasGroupAlpha(canvasGroup)
.ToUniTask(CancellationTokenSource.CreateLinkedTokenSource(destroyCancellationToken, cancellationToken).Token);
}
}
Prefab the created Page objects for convenience. By adding Prefabed Pages using PushNewObjectAsync() or AddNewObjectAsync(), you can manage object generation/destruction based on the Page lifecycle.
Page prefab;
NavigationStack navigationStack;
NavigationSheet navigationSheet;
await navigationStack.PushNewObjectAsync(prefab);
await navigationSheet.AddNewObjectAsync(prefab);
Content Management
TODO
R3
TODO
VContainer
TODO
No comments yet. Be the first!