summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/com/vaadin/navigator/Navigator.java316
-rw-r--r--tests/server-side/com/vaadin/tests/server/navigator/ClassBasedViewProviderTest.java175
-rw-r--r--tests/server-side/com/vaadin/tests/server/navigator/NavigatorTest.java245
3 files changed, 462 insertions, 274 deletions
diff --git a/src/com/vaadin/navigator/Navigator.java b/src/com/vaadin/navigator/Navigator.java
index 7c2cd1df55..9d9acf9ed3 100644
--- a/src/com/vaadin/navigator/Navigator.java
+++ b/src/com/vaadin/navigator/Navigator.java
@@ -5,7 +5,7 @@
package com.vaadin.navigator;
import java.io.Serializable;
-import java.util.HashMap;
+import java.util.Iterator;
import java.util.LinkedList;
import java.util.List;
@@ -39,12 +39,15 @@ public class Navigator implements Serializable {
// TODO divert navigation e.g. if no permissions? Or just show another view
// but keep URL? how best to intercept
- // TODO investigate relationship to TouchKit navigation support
+ // TODO investigate relationship with TouchKit navigation support
/**
* Empty view component.
*/
public static class EmptyView extends CssLayout implements View {
+ /**
+ * Create minimally sized empty view.
+ */
public EmptyView() {
setWidth("0px");
setHeight("0px");
@@ -75,7 +78,7 @@ public class Navigator implements Serializable {
* root whose URI fragment to get and modify
* @param navigator
* {@link Navigator} to notify of fragment changes (using
- * {@link Navigator#navigateTo(String, Object...)}
+ * {@link Navigator#navigateTo(String)}
*/
public UriFragmentManager(Root root, Navigator navigator) {
this.root = root;
@@ -130,105 +133,105 @@ public class Navigator implements Serializable {
}
/**
- * View provider which uses a map from view name to pre-created and
- * registered view instances.
+ * View provider which supports mapping a single view name to a single
+ * pre-initialized view instance.
+ *
+ * For most cases, ClassBasedViewProvider should be used instead of this.
*/
- public static class RegisteredViewProvider implements ViewProvider {
+ public static class StaticViewProvider implements ViewProvider {
+ private final String viewName;
+ private final View view;
- private HashMap<String, View> viewNameToView = new HashMap<String, View>();
+ /**
+ * Create a new view provider which returns a pre-created view instance.
+ *
+ * @param viewName
+ * name of the view (not null)
+ * @param view
+ * view instance to return (not null), reused on every
+ * request
+ */
+ public StaticViewProvider(String viewName, View view) {
+ this.viewName = viewName;
+ this.view = view;
+ }
public String getViewName(String viewAndParameters) {
if (null == viewAndParameters) {
return null;
}
- for (String viewName : viewNameToView.keySet()) {
- if (viewAndParameters.equals(viewName)
- || viewAndParameters.startsWith(viewName + "/")) {
- return viewName;
- }
+ if (viewAndParameters.startsWith(viewName)) {
+ return viewName;
}
return null;
}
public View getView(String viewName) {
- return viewNameToView.get(viewName);
- }
-
- /**
- * Register a view for a view name.
- *
- * Registering another view with a name that is already registered
- * overwrites the old registration.
- *
- * @param viewName
- * String that identifies a view (not null nor empty string)
- * @param view
- * {@link View} instance (not null)
- */
- public void addView(String viewName, View view) {
-
- // Check parameters
- if (viewName == null || view == null || viewName.length() == 0) {
- throw new IllegalArgumentException(
- "view and viewName must be non-null and not empty");
+ if (this.viewName.equals(viewName)) {
+ return view;
}
-
- viewNameToView.put(viewName, view);
+ return null;
}
/**
- * Remove view from navigator.
+ * Get the view name for this provider.
*
- * @param viewName
- * name of the view to remove
+ * @return view name for this provider
*/
- public void removeView(String viewName) {
- viewNameToView.remove(viewName);
+ public String getViewName() {
+ return viewName;
}
}
/**
- * View provider which uses a map from view name to the class to instantiate
- * for the view.
- *
- * Views that have been created are cached and reused when the same view
- * name is requested again.
+ * View provider which maps a single view name to a class to instantiate for
+ * the view.
*
* Note that the view class must be accessible by the class loader used by
* the provider. This may require its visibility to be public.
+ *
+ * This class is primarily for internal use by {@link Navigator}.
*/
public static class ClassBasedViewProvider implements ViewProvider {
- private HashMap<String, Class<? extends View>> viewNameToClass = new HashMap<String, Class<? extends View>>();
- private HashMap<Class<? extends View>, String> classToViewName = new HashMap<Class<? extends View>, String>();
+ private final String viewName;
+ private final Class<? extends View> viewClass;
+
/**
- * Already opened (cached) views that can be reopened or reused with new
- * parameters.
+ * Create a new view provider which creates new view instances based on
+ * a view class.
+ *
+ * @param viewName
+ * name of the views to create (not null)
+ * @param viewClass
+ * class to instantiate when a view is requested (not null)
*/
- private HashMap<Class<? extends View>, View> classToView = new HashMap<Class<? extends View>, View>();
+ public ClassBasedViewProvider(String viewName,
+ Class<? extends View> viewClass) {
+ if (null == viewName || null == viewClass) {
+ throw new IllegalArgumentException(
+ "View name and class should not be null");
+ }
+ this.viewName = viewName;
+ this.viewClass = viewClass;
+ }
public String getViewName(String viewAndParameters) {
if (null == viewAndParameters) {
return null;
}
- for (String viewName : viewNameToClass.keySet()) {
- if (viewAndParameters.equals(viewName)
- || viewAndParameters.startsWith(viewName + "/")) {
- return viewName;
- }
+ if (viewAndParameters.equals(viewName)
+ || viewAndParameters.startsWith(viewName + "/")) {
+ return viewName;
}
return null;
}
public View getView(String viewName) {
- Class<? extends View> newViewClass = viewNameToClass.get(viewName);
- if (null == newViewClass) {
- return null;
- }
- if (!classToView.containsKey(newViewClass)) {
+ if (this.viewName.equals(viewName)) {
try {
- View view = newViewClass.newInstance();
- classToView.put(newViewClass, view);
+ View view = viewClass.newInstance();
+ return view;
} catch (InstantiationException e) {
// TODO error handling
throw new RuntimeException(e);
@@ -237,89 +240,25 @@ public class Navigator implements Serializable {
throw new RuntimeException(e);
}
}
- // return already cached view
- final View v = classToView.get(newViewClass);
- return v;
- }
-
- /**
- * Register a view class for a view name.
- *
- * @param viewName
- * String that identifies a view (not null nor empty string)
- * @param viewClass
- * Component class that implements Navigator.View interface
- * (not null)
- */
- public void addView(String viewName, Class<? extends View> viewClass) {
-
- // Check parameters
- if (viewName == null || viewClass == null || viewName.length() == 0) {
- throw new IllegalArgumentException(
- "viewClass and viewName must be non-null and not empty");
- }
-
- if (!View.class.isAssignableFrom(viewClass)) {
- throw new IllegalArgumentException(
- "viewClass must implement Navigator.View");
- }
-
- if (viewNameToClass.containsKey(viewName)) {
- if (viewNameToClass.get(viewName) == viewClass) {
- return;
- }
-
- throw new IllegalArgumentException(viewNameToClass
- .get(viewName).getName()
- + " is already mapped to '"
- + viewName + "'");
- }
-
- if (classToViewName.containsKey(viewClass)) {
- throw new IllegalArgumentException(
- "Each view class can only be added to Navigator with one view name");
- }
-
- viewNameToClass.put(viewName, viewClass);
- classToViewName.put(viewClass, viewName);
- }
-
- /**
- * Remove view from navigator.
- *
- * @param viewName
- * name of the view to remove
- */
- public void removeView(String viewName) {
- Class<? extends View> c = viewNameToClass.get(viewName);
- if (c != null) {
- viewNameToClass.remove(viewName);
- classToViewName.remove(c);
- classToView.remove(c);
- }
+ return null;
}
/**
- * Get the view name for given view implementation class.
+ * Get the view name for this provider.
*
- * @param viewClass
- * Class that implements the view.
- * @return view name for which the view class is registered, null if
- * none
+ * @return view name for this provider
*/
- public String getViewName(Class<? extends View> viewClass) {
- return classToViewName.get(viewClass);
+ public String getViewName() {
+ return viewName;
}
/**
- * Get the view class for given view name.
+ * Get the view class for this provider.
*
- * @param viewName
- * view name to get view for
- * @return View that corresponds to the name
+ * @return {@link View} class
*/
- public Class<? extends View> getViewClass(String viewName) {
- return viewNameToClass.get(viewName);
+ public Class<? extends View> getViewClass() {
+ return viewClass;
}
}
@@ -380,29 +319,42 @@ public class Navigator implements Serializable {
* and (fragment) parameters. ViewProviders are used to find and create the
* correct type of view.
*
- * If the view being left indicates it wants a confirmation for the
+ * If multiple providers return a matching view, the view with the longest
+ * name is selected. This way, e.g. hierarchies of subviews can be
+ * registered like "admin/", "admin/users", "admin/settings" and the longest
+ * match is used.
+ *
+ * If the view being deactivated indicates it wants a confirmation for the
* navigation operation, the user is asked for the confirmation.
*
+ * Registered {@link ViewChangeListener}s are called upon successful view
+ * change.
+ *
* @param viewAndParameters
* view name and parameters
*/
public void navigateTo(String viewAndParameters) {
+ String longestViewName = "";
+ View viewWithLongestName = null;
for (ViewProvider provider : providers) {
String viewName = provider.getViewName(viewAndParameters);
- if (null != viewName) {
- String parameters = null;
- if (viewAndParameters.length() > viewName.length() + 1) {
- parameters = viewAndParameters
- .substring(viewName.length() + 1);
- }
+ if (null != viewName
+ && viewName.length() > longestViewName.length()) {
View view = provider.getView(viewName);
if (null != view) {
- navigateTo(view, viewName, parameters);
- // stop after a view is found
- return;
+ longestViewName = viewName;
+ viewWithLongestName = view;
}
}
}
+ if (viewWithLongestName != null) {
+ String parameters = null;
+ if (viewAndParameters.length() > longestViewName.length() + 1) {
+ parameters = viewAndParameters.substring(longestViewName
+ .length() + 1);
+ }
+ navigateTo(viewWithLongestName, longestViewName, parameters);
+ }
// TODO if no view is found, what to do?
}
@@ -506,6 +458,82 @@ public class Navigator implements Serializable {
}
/**
+ * Register a static, pre-initialized view instance for a view name.
+ *
+ * Registering another view with a name that is already registered
+ * overwrites the old registration of the same type.
+ *
+ * @param viewName
+ * String that identifies a view (not null nor empty string)
+ * @param view
+ * {@link View} instance (not null)
+ */
+ public void addView(String viewName, View view) {
+
+ // Check parameters
+ if (viewName == null || view == null) {
+ throw new IllegalArgumentException(
+ "view and viewName must be non-null");
+ }
+
+ removeView(viewName);
+ registerProvider(new StaticViewProvider(viewName, view));
+ }
+
+ /**
+ * Register for a view name a view class.
+ *
+ * Registering another view with a name that is already registered
+ * overwrites the old registration of the same type.
+ *
+ * A new view instance is created every time a view is requested.
+ *
+ * @param viewName
+ * String that identifies a view (not null nor empty string)
+ * @param viewClass
+ * {@link View} class to instantiate when a view is requested
+ * (not null)
+ */
+ public void addView(String viewName, Class<? extends View> viewClass) {
+
+ // Check parameters
+ if (viewName == null || viewClass == null) {
+ throw new IllegalArgumentException(
+ "view and viewClass must be non-null");
+ }
+
+ removeView(viewName);
+ registerProvider(new ClassBasedViewProvider(viewName, viewClass));
+ }
+
+ /**
+ * Remove view from navigator.
+ *
+ * This method only applies to views registered using
+ * {@link #addView(String, View)} or {@link #addView(String, Class)}.
+ *
+ * @param viewName
+ * name of the view to remove
+ */
+ public void removeView(String viewName) {
+ Iterator<ViewProvider> it = providers.iterator();
+ while (it.hasNext()) {
+ ViewProvider provider = it.next();
+ if (provider instanceof StaticViewProvider) {
+ StaticViewProvider staticProvider = (StaticViewProvider) provider;
+ if (staticProvider.getViewName().equals(viewName)) {
+ it.remove();
+ }
+ } else if (provider instanceof ClassBasedViewProvider) {
+ ClassBasedViewProvider classBasedProvider = (ClassBasedViewProvider) provider;
+ if (classBasedProvider.getViewName().equals(viewName)) {
+ it.remove();
+ }
+ }
+ }
+ }
+
+ /**
* Register a view provider (factory).
*
* Providers are called in order of registration until one that can handle
diff --git a/tests/server-side/com/vaadin/tests/server/navigator/ClassBasedViewProviderTest.java b/tests/server-side/com/vaadin/tests/server/navigator/ClassBasedViewProviderTest.java
index 72d595bc7d..fc0d1b60a0 100644
--- a/tests/server-side/com/vaadin/tests/server/navigator/ClassBasedViewProviderTest.java
+++ b/tests/server-side/com/vaadin/tests/server/navigator/ClassBasedViewProviderTest.java
@@ -12,8 +12,6 @@ import com.vaadin.ui.Label;
public class ClassBasedViewProviderTest extends TestCase {
- private ClassBasedViewProvider provider;
-
public static class TestView extends Label implements View {
public String parameters = null;
@@ -27,86 +25,68 @@ public class ClassBasedViewProviderTest extends TestCase {
}
- @Override
- protected void setUp() throws Exception {
- super.setUp();
- provider = new ClassBasedViewProvider();
- }
-
- public void testAddViewWithNullName() throws Exception {
+ public void testCreateProviderWithNullName() throws Exception {
try {
- provider.addView(null, TestView.class);
- fail("Should not be able to add view with null name");
+ new ClassBasedViewProvider(null, TestView.class);
+ fail("Should not be able to create view provider with null name");
} catch (IllegalArgumentException e) {
}
}
- public void testAddViewWithEmptyStringName() throws Exception {
- try {
- provider.addView("", TestView.class);
- fail("Should not be able to add view with empty name");
- } catch (IllegalArgumentException e) {
- }
+ public void testCreateProviderWithEmptyStringName() throws Exception {
+ new ClassBasedViewProvider("", TestView.class);
}
- public void testAddViewNull() throws Exception {
+ public void testCreateProviderNullViewClass() throws Exception {
try {
- provider.addView("test", null);
- fail("Should not be able to add null view");
+ new ClassBasedViewProvider("test", null);
+ fail("Should not be able to create view provider with null view class");
} catch (IllegalArgumentException e) {
}
}
- public void testAddViewSameName() throws Exception {
- try {
- provider.addView("test", TestView.class);
- provider.addView("test", TestView2.class);
- fail("Should not be able to add two views with same name");
- } catch (IllegalArgumentException e) {
- }
+ public void testViewNameGetter() throws Exception {
+ ClassBasedViewProvider provider1 = new ClassBasedViewProvider("",
+ TestView.class);
+ assertEquals("View name should be empty", "", provider1.getViewName());
+
+ ClassBasedViewProvider provider2 = new ClassBasedViewProvider("test",
+ TestView.class);
+ assertEquals("View name does not match", "test",
+ provider2.getViewName());
}
- public void testAddViewSameClass() throws Exception {
- try {
- provider.addView("test", TestView.class);
- provider.addView("test2", TestView.class);
- fail("Should not be able to add same view class with two different names");
- } catch (IllegalArgumentException e) {
- }
+ public void testViewClassGetter() throws Exception {
+ ClassBasedViewProvider provider = new ClassBasedViewProvider("test",
+ TestView.class);
+ assertEquals("Incorrect view class returned by getter", TestView.class,
+ provider.getViewClass());
}
public void testGetViewNameForNullString() throws Exception {
- assertNull(
- "Found view name for null view string in an empty view provider",
- provider.getViewName((String) null));
-
- provider.addView("test", TestView.class);
- assertNull("Found view name for null view string",
+ ClassBasedViewProvider provider = new ClassBasedViewProvider("test",
+ TestView.class);
+ assertNull("Received view name for null view string",
provider.getViewName((String) null));
}
- public void testGetViewNameForNullClass() throws Exception {
- assertNull("Found view name for null class",
- provider.getViewName((Class<View>) null));
- }
-
public void testGetViewNameForEmptyString() throws Exception {
- assertNull(
- "Found view name for empty view string in an empty provider",
- provider.getViewName(""));
- provider.addView("test", TestView.class);
- assertNull("Found view name for empty view string",
- provider.getViewName(""));
- }
+ ClassBasedViewProvider provider1 = new ClassBasedViewProvider("",
+ TestView.class);
+ assertEquals(
+ "Did not find view name for empty view string in a provider with empty string registered",
+ "", provider1.getViewName(""));
- public void testGetViewNameForClass() throws Exception {
- provider.addView("test", TestView.class);
- assertEquals("No view name found for view class", "test",
- provider.getViewName(TestView.class));
+ ClassBasedViewProvider provider2 = new ClassBasedViewProvider("test",
+ TestView.class);
+ assertNull(
+ "Found view name for empty view string when none registered",
+ provider2.getViewName(""));
}
public void testGetViewNameWithParameters() throws Exception {
- provider.addView("test", TestView.class);
+ ClassBasedViewProvider provider = new ClassBasedViewProvider("test",
+ TestView.class);
assertEquals("Incorrect view name found for view string", "test",
provider.getViewName("test"));
assertEquals(
@@ -117,86 +97,21 @@ public class ClassBasedViewProviderTest extends TestCase {
"test", provider.getViewName("test/params/are/here"));
}
- public void testGetViewNameMultipleRegisteredWithParameters()
- throws Exception {
- provider.addView("test", TestView.class);
- provider.addView("test2", TestView2.class);
- assertEquals("Incorrect view name found for view string", "test",
- provider.getViewName("test/test2/params"));
- }
+ public void testGetView() throws Exception {
+ ClassBasedViewProvider provider = new ClassBasedViewProvider("test",
+ TestView.class);
- public void testGetViewNameNestedNames() throws Exception {
- provider.addView("test/subview", TestView2.class);
- provider.addView("test", TestView.class);
- assertEquals("Incorrect view name found for subview string",
- "test/subview", provider.getViewName("test/subview"));
- assertEquals(
- "Incorrect view name found for subview string with empty parameters",
- "test/subview", provider.getViewName("test/subview/"));
- assertEquals(
- "Incorrect view name found for subview string with parameters",
- "test/subview", provider.getViewName("test/subview/parameters"));
- assertEquals("Incorrect view name found for top level view string",
- "test", provider.getViewName("test"));
- assertEquals(
- "Incorrect view name found for top level view string with empty parameters",
- "test", provider.getViewName("test/"));
- assertEquals(
- "Incorrect view name found for top level view string with parameters starting like subview name",
- "test", provider.getViewName("test/subviewnothere"));
- }
-
- public void testGetViewClass() throws Exception {
- assertNull("View class found for empty view provider",
- provider.getViewClass("test"));
- provider.addView("test", TestView.class);
- assertEquals("View class not found", TestView.class,
- provider.getViewClass("test"));
- assertNull("View class found for unregistered view name",
- provider.getViewClass("test2"));
- }
-
- public void testGetViewSimple() throws Exception {
- assertNull("Found view in an empty view provider",
- provider.getViewName("test"));
-
- provider.addView("test", TestView.class);
View view = provider.getView("test");
assertNotNull("Did not get view from a provider", view);
assertEquals("Incorrect view type", TestView.class, view.getClass());
}
- public void testGetViewMultipleRegistered() throws Exception {
- provider.addView("test", TestView.class);
- provider.addView("test2", TestView2.class);
- assertEquals("Incorrect view type", TestView.class,
- provider.getView("test").getClass());
- assertEquals("Incorrect view type", TestView2.class,
- provider.getView("test2").getClass());
- assertEquals("Incorrect view type", TestView.class,
- provider.getView("test").getClass());
- }
-
- public void testRemoveView() throws Exception {
- provider.addView("test", TestView.class);
- assertNotNull("Did not get view from a provider",
- provider.getView("test"));
- provider.removeView("test");
- assertNull("View class found for removed view name",
- provider.getViewClass("test"));
- assertNull("View name found for removed view",
- provider.getViewName(TestView.class));
- // cached view?
- assertNull(
- "Received view instance from a provider after removing view type",
- provider.getView("test"));
- }
+ public void testGetViewIncorrectViewName() throws Exception {
+ ClassBasedViewProvider provider = new ClassBasedViewProvider("test",
+ TestView.class);
- public void testGetViewCached() throws Exception {
- provider.addView("test", TestView.class);
- View view1 = provider.getView("test");
- View view2 = provider.getView("test");
- assertSame("View instance not cached", view1, view2);
+ View view = provider.getView("test2");
+ assertNull("Got view from a provider for incorrect view name", view);
}
}
diff --git a/tests/server-side/com/vaadin/tests/server/navigator/NavigatorTest.java b/tests/server-side/com/vaadin/tests/server/navigator/NavigatorTest.java
index 49cd82c2e3..ab983b4022 100644
--- a/tests/server-side/com/vaadin/tests/server/navigator/NavigatorTest.java
+++ b/tests/server-side/com/vaadin/tests/server/navigator/NavigatorTest.java
@@ -13,17 +13,60 @@ import org.easymock.IMocksControl;
import com.vaadin.navigator.FragmentManager;
import com.vaadin.navigator.Navigator;
+import com.vaadin.navigator.Navigator.SimpleViewDisplay;
import com.vaadin.navigator.View;
import com.vaadin.navigator.ViewChangeListener;
import com.vaadin.navigator.ViewChangeListener.ViewChangeEvent;
import com.vaadin.navigator.ViewDisplay;
import com.vaadin.navigator.ViewProvider;
+import com.vaadin.tests.server.navigator.ClassBasedViewProviderTest.TestView;
+import com.vaadin.tests.server.navigator.ClassBasedViewProviderTest.TestView2;
+import com.vaadin.ui.Root;
public class NavigatorTest extends TestCase {
// TODO test internal parameters (and absence of them)
// TODO test listeners blocking navigation, multiple listeners
+ public static class NullDisplay implements ViewDisplay {
+ public void showView(View view) {
+ // do nothing
+ }
+ }
+
+ public static class NullFragmentManager implements FragmentManager {
+ public String getFragment() {
+ return null;
+ }
+
+ public void setFragment(String fragment) {
+ // do nothing
+ }
+ }
+
+ public static class TestDisplay implements ViewDisplay {
+ private View currentView;
+
+ public void showView(View view) {
+ currentView = view;
+ }
+
+ public View getCurrentView() {
+ return currentView;
+ }
+ }
+
+ public static class TestNavigator extends Navigator {
+ public TestNavigator() {
+ super(new NullFragmentManager(), new TestDisplay());
+ }
+
+ public View getView(String viewAndParameters) {
+ navigateTo(viewAndParameters);
+ return ((TestDisplay) getDisplay()).getCurrentView();
+ }
+ }
+
public static class ViewChangeTestListener implements ViewChangeListener {
private final LinkedList<ViewChangeEvent> referenceEvents = new LinkedList<ViewChangeListener.ViewChangeEvent>();
private final LinkedList<Boolean> referenceIsCheck = new LinkedList<Boolean>();
@@ -321,4 +364,206 @@ public class NavigatorTest extends TestCase {
}
}
+ public void testDefaultDisplayType() {
+ IMocksControl control = EasyMock.createControl();
+ Root root = control.createMock(Root.class);
+
+ Navigator navigator = new Navigator(root);
+
+ assertEquals("Default display should be a SimpleViewDisplay",
+ SimpleViewDisplay.class, navigator.getDisplay().getClass());
+ }
+
+ public void testAddViewInstance() throws Exception {
+ View view = new TestView();
+
+ TestNavigator navigator = new TestNavigator();
+
+ navigator.addView("test", view);
+
+ assertEquals("Registered view instance not returned by navigator",
+ view, navigator.getView("test"));
+ }
+
+ public void testAddViewInstanceSameName() throws Exception {
+ View view1 = new TestView();
+ View view2 = new TestView2();
+
+ TestNavigator navigator = new TestNavigator();
+
+ navigator.addView("test", view1);
+ navigator.addView("test", view2);
+
+ assertEquals(
+ "Adding second view with same name should override previous view",
+ view2, navigator.getView("test"));
+ }
+
+ public void testAddViewClass() throws Exception {
+ TestNavigator navigator = new TestNavigator();
+
+ navigator.addView("test", TestView.class);
+
+ View view = navigator.getView("test");
+ assertNotNull("Received null view", view);
+ assertEquals("Received incorrect type of view", TestView.class,
+ view.getClass());
+ }
+
+ public void testAddViewClassSameName() throws Exception {
+ TestNavigator navigator = new TestNavigator();
+
+ navigator.addView("test", TestView.class);
+ navigator.addView("test", TestView2.class);
+
+ assertEquals(
+ "Adding second view class with same name should override previous view",
+ TestView2.class, navigator.getView("test").getClass());
+ }
+
+ public void testAddViewInstanceAndClassSameName() throws Exception {
+ TestNavigator navigator = new TestNavigator();
+
+ navigator.addView("test", TestView.class);
+ TestView2 view2 = new TestView2();
+ navigator.addView("test", view2);
+
+ assertEquals(
+ "Adding second view class with same name should override previous view",
+ view2, navigator.getView("test"));
+
+ navigator.addView("test", TestView.class);
+
+ assertEquals(
+ "Adding second view class with same name should override previous view",
+ TestView.class, navigator.getView("test").getClass());
+ }
+
+ public void testAddViewWithNullName() throws Exception {
+ Navigator navigator = new Navigator(new NullFragmentManager(),
+ new NullDisplay());
+
+ try {
+ navigator.addView(null, new TestView());
+ fail("addView() accepted null view name");
+ } catch (IllegalArgumentException e) {
+ }
+ try {
+ navigator.addView(null, TestView.class);
+ fail("addView() accepted null view name");
+ } catch (IllegalArgumentException e) {
+ }
+ }
+
+ public void testAddViewWithNullInstance() throws Exception {
+ Navigator navigator = new Navigator(new NullFragmentManager(),
+ new NullDisplay());
+
+ try {
+ navigator.addView("test", (View) null);
+ fail("addView() accepted null view instance");
+ } catch (IllegalArgumentException e) {
+ }
+ }
+
+ public void testAddViewWithNullClass() throws Exception {
+ Navigator navigator = new Navigator(new NullFragmentManager(),
+ new NullDisplay());
+
+ try {
+ navigator.addView("test", (Class<View>) null);
+ fail("addView() accepted null view class");
+ } catch (IllegalArgumentException e) {
+ }
+ }
+
+ public void testRemoveViewInstance() throws Exception {
+ View view = new TestView();
+
+ TestNavigator navigator = new TestNavigator();
+
+ navigator.addView("test", view);
+ navigator.removeView("test");
+
+ assertNull("View not removed", navigator.getView("test"));
+ }
+
+ public void testRemoveViewInstanceNothingElse() throws Exception {
+ View view = new TestView();
+ View view2 = new TestView2();
+
+ TestNavigator navigator = new TestNavigator();
+
+ navigator.addView("test", view);
+ navigator.addView("test2", view2);
+ navigator.removeView("test");
+
+ assertEquals("Removed extra views", view2, navigator.getView("test2"));
+ }
+
+ public void testRemoveViewClass() throws Exception {
+ TestNavigator navigator = new TestNavigator();
+
+ navigator.addView("test", TestView.class);
+ navigator.removeView("test");
+
+ assertNull("View not removed", navigator.getView("test"));
+ }
+
+ public void testRemoveViewClassNothingElse() throws Exception {
+ TestNavigator navigator = new TestNavigator();
+
+ navigator.addView("test", TestView.class);
+ navigator.addView("test2", TestView2.class);
+ navigator.removeView("test");
+
+ assertEquals("Removed extra views", TestView2.class,
+ navigator.getView("test2").getClass());
+ }
+
+ public void testGetViewNestedNames() throws Exception {
+ TestNavigator navigator = new TestNavigator();
+
+ navigator.addView("test/subview", TestView2.class);
+ navigator.addView("test", TestView.class);
+
+ assertEquals("Incorrect view name found for subview string",
+ TestView2.class, navigator.getView("test/subview").getClass());
+ assertEquals(
+ "Incorrect view name found for subview string with empty parameters",
+ TestView2.class, navigator.getView("test/subview/").getClass());
+ assertEquals(
+ "Incorrect view name found for subview string with parameters",
+ TestView2.class, navigator.getView("test/subview/parameters")
+ .getClass());
+ assertEquals("Incorrect view name found for top level view string",
+ TestView.class, navigator.getView("test").getClass());
+ assertEquals(
+ "Incorrect view name found for top level view string with empty parameters",
+ TestView.class, navigator.getView("test/").getClass());
+ assertEquals(
+ "Incorrect view name found for top level view string with parameters starting like subview name",
+ TestView.class, navigator.getView("test/subviewnothere")
+ .getClass());
+ }
+
+ public void testGetViewLongestPrefixOrder() throws Exception {
+ TestNavigator navigator = new TestNavigator();
+
+ navigator.addView("test/subview", TestView2.class);
+ navigator.addView("test", TestView.class);
+
+ assertEquals("Incorrect view name found", TestView.class, navigator
+ .getView("test").getClass());
+
+ // other order
+
+ TestNavigator navigator2 = new TestNavigator();
+
+ navigator2.addView("test", TestView.class);
+ navigator2.addView("test/subview", TestView2.class);
+
+ assertEquals("Incorrect view name found", TestView.class, navigator2
+ .getView("test").getClass());
+ }
}