MVP plus Activity/Places

July 4, 2011 at 8:38 pm Leave a comment

I have been through the new GWT 2.1  HelloMVP example , but I was disappointed that for a new technique, it was just to simple of a scenario. I wanted a more involved use case to show the merits of the Activities / Places.  Luckily, I came across the Ashton Thomas GWT 2.1 seminar example and tutorial .

Starting off in the gwt.xml of this GWT 2.1 project:

<!-- Inherit GIN. -->
    <inherits name='com.google.gwt.inject.Inject'/>
<!-- Inherit Activity -->
    <inherits name='com.google.gwt.activity.Activity'/>
<!-- Inherit Place. -->
    <inherits name='com.google.gwt.place.Place'/>
<!-- Inherit Resources -->
    <inherits name='com.google.gwt.resources.Resources'/>

The class AcrintaSeminar is the entry point class.
DesktopInjector is a gin injector  interface that defines method  getAcrintaSeminarApp()  which returns  DesktopApp.
The class AppInjectorModule does the gin injecting:

  • event bus: SimpleEventBus
  • placeController: PlaceControllerProvider

Place: A place basically represents a certain state of your UI. The place is identified using a name. The place string you provide is bascially the history token that will trigger things such as a presenter to activate.

public abstract class AppPlace extends Place {
	public abstract String getToken();
}

PlaceController: In charge of the user’s location in the GUI.

public class PlaceControllerProvider implements Provider<PlaceController>{
	// set up the evenBus to be injected via the constructor
	private final EventBus eventBus;

Activity: is analogous to a presenter in MVP terminology. Activities are started and stopped by an ActivityManager associated with a container Widget.

public class HomeActivity extends AbstractActivity {
	private HomeView view;
	...
	@Override
	public void start(AcceptsOneWidget panel, EventBus eventBus) {
		panel.setWidget(view.asWidget());

	}

Activity Mapper: Returns the activity to run for the given place

public class MainActivityMapper implements ActivityMapper {…

@Inject
	public MainActivityMapper(HomeActivity homeActivity, RsvpActivity rsvpActivity, AboutActivity aboutActivity,
								ContactActivity contactActivity, LocationActivity locationActivity, ResourcesActivity resourcesActivity){
		...

	public Activity getActivity(Place place) {
		// there are other ways of doing this
		// but just check the instnaces and return
		// the appropriate Activity
		if(place instanceof HomePlace){
			return homeActivity;
		}

ActivityManager: with a given place event, it associates a representative activity to invoke. Here you can start or stop activities where they are associated with a particular widget.

public class DesktopApp extends AcrintaSeminarApp {
	private final DesktopShell shell;
	private final EventBus eventBus;
	private final PlaceController placeController;
	private final MainActivityMapper mainActivityMapper;
	private final AppPlaceHistoryMapper appPlaceHistoryMapper;

	....

	public void run(){
		/* Add handlers, setup activities */
		GWT.setUncaughtExceptionHandler(new GWT.UncaughtExceptionHandler() {
			public void onUncaughtException(Throwable e) {
				Window.alert("Hey, something went wrong: " + e.getMessage());
				// we could log this if we were using logging...

			}
		});

		CachingActivityMapper cached = new CachingActivityMapper(mainActivityMapper);
		final ActivityManager mainActivityManager = new ActivityManager(cached, eventBus);

		mainActivityManager.setDisplay(shell.getContent());


PlaceHistoryMapper: attach all places which the PlaceHistoryHandler should be aware of.

public class AppPlaceHistoryMapper implements PlaceHistoryMapper{

	private HomePlace homePlace;
	private RsvpPlace rsvpPlace;
	...
@Override
	public Place getPlace(String token) {

		if(token.startsWith("home")){
			return homePlace;
		}else if(token.startsWith("rsvp")){
			return rsvpPlace;
		}else if(token.startsWith("about")){
			return aboutPlace;
		}else if(token.startsWith("contact")){
			return contactPlace;
		}else if (token.startsWith("location")){
			return locationPlace;
		}else if(token.startsWith("resources")){
			return resourcesPlace;
		}

		return null;
	}

	@Override
	public Place getPlace(String token) {

		if(token.startsWith("home")){
			return homePlace;

PlaceHistoryHandler: updates the browser URL corresponding to each Place in your app.

public class DesktopApp extends AcrintaSeminarApp {
	private final DesktopShell shell;
	private final EventBus eventBus;
	private final PlaceController placeController;
	private final MainActivityMapper mainActivityMapper;
	private final AppPlaceHistoryMapper appPlaceHistoryMapper;

	....

	public void run(){
        ....
// History management
		AppPlaceHistoryMapper historyMapper = appPlaceHistoryMapper;
		PlaceHistoryHandler historyHandler = new PlaceHistoryHandler(historyMapper);
		historyHandler.register(placeController, eventBus, defaultPlace);

		// add out UiBinder shell to the Root Panel (the main html document thingy)
		RootLayoutPanel.get().add(shell);
		historyHandler.handleCurrentHistory();

Entry filed under: Uncategorized.

Easy To Use UI Binder in your GWT Getting to know the gwt xml file better

Leave a comment

Trackback this post  |  Subscribe to the comments via RSS Feed