Skip to content

Implementation of MVP (Model-View-Presenter) architectural pattern via Unity engine.

License

Notifications You must be signed in to change notification settings

dancher743/unity-mvp

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

9 Commits
 
 
 
 
 
 
 
 

Repository files navigation

unity-mvp

Implementation of MVP (Model-View-Presenter) architectural pattern via Unity engine.

Sample

Before to start, it's recommended to get sample project with the latest version of the package.

Getting Started

What is MVP?

MVP or Model-View-Presenter is an architectural pattern, which consists of three components: Model, View and Presenter.

  • Model is a data.
  • View is an interface that displays data and routes user commands to Presenter.
  • Presenter wires up Model and View together and thereby creates a functioning entity.

MVP-diagram.png

For more information about MVP, check an original source - "MVP: Model-View-Presenter. The Taligent Programming Model for C++ and Java." Mike Potel.

Creating a Model

Implement IModel interface to create a Model -

public class CubeModel : IModel
{
	// ...
}

Creating a View

Implement IView interface to create a View -

public class CubeView : MonoBehaviour, IView
{
	// ...
}

You can also use MonoView class as an "stub" instead of MonoBehaviour -

public class CubeView : MonoView, IView

Creating a Presenter

Create a CubePresenter class and derive it from Presenter<TView, TModel>. Specify types: TView and TModel. In our case TModel is CubeModel and TView is CubeView -

CubePresenter : Presenter<CubeView, CubeModel>

public class CubePresenter : Presenter<CubeView, CubeModel>
{
	public CubePresenter(CubeView cubeView, CubeModel cubeModel) : base(cubeView, cubeModel)
	{
		// ...
	}
}

At this point we're done with the main components of MVP - CubeModel, CubeView and CubePresenter!

Instancing

To create an instance of a Presenter use Create<TPresenter>() method in PresenterFactory -

[SerializeField]
private CubeView cubeView;

// ...

private CubePresenter cubePresenter;

// ...

void Start()
{
	cubePresenter = presenterFactory.Create<CubePresenter>(cubeView, new CubeModel());
}

PresenterFactory is built-in implementation of IPresenterFactory interface -

public interface IPresenterFactory
{
	public TPresenter Create<TPresenter>(params object[] data) where TPresenter : IPresenter;
}

But you can implement your own factory.

Messaging

Message Dispatcher

Each Presenter should interact with another Presenter. One possible way to do it is to use messages. MessageDispatcher is a class which provides needed functionality for messaging.

But to receive a Message we need a Subscriber.

Receive a Message

Implement IMessageSubscriber interface to make some class available for message receiving -

public interface IMessageSubscriber
{
	void ReceiveMessage<TMessage>(TMessage message);
}

In the example we have UIPresenter -

public class UIPresenter : Presenter<UIView, UIModel>, IMessageSubscriber
{
	// ...
	
	void IMessageSubscriber.ReceiveMessage<TMessage>(TMessage message)
	{
		switch (message)
		{
			case CubeColorMessage cubeColorMessage:
				model.ColorText = cubeColorMessage.Color.ToString();
				break;
		}
	}
}

Switch-case is used here as a way to handle a message from CubePresenter.

Send a Message

To send a Message to some Presenter use DispatchMessageTo<TSubscriber, TMessage>(TMessage message) method in MessageDispatcher -

MessageDispatcher.DispatchMessageTo<UIPresenter, CubeColorData>(new CubeColorData(color))

In the example where CubePresenter class is -

public class CubePresenter : Presenter<CubeView, CubeModel>
{
  	// ...

	private void OnModelColorChanged(Color color)
	{
		view.Color = color;
		messageDispatcher.DispatchMessageTo<UIPresenter, CubeColorMessage>(new CubeColorMessage { Color = color });
	}
}

Clearing

To clear a Presenter (or some class) you can use built-in IClearable interface -

public interface IClearable
{
	public void Clear();
}

Base Presenter class implements IClearable interface -

Presenter<TView, TModel> : IPresenter, IClearable

In the example, inside of EntryPoint.OnDestroy() method Clear is used to free up resources -

public class EntryPoint : MonoBehaviour
{
	// ...
	
	private CubePresenter cubePresenter;
	private UIPresenter UIPresenter;

	// ...

	private void OnDestroy()
	{
		cubePresenter.Clear();
		UIPresenter.Clear();
	}
{