Fix for event handling bug in nested StackPanels (issue 834).
Issue: 834
Patch by: bobv
Review by: jgw


git-svn-id: https://google-web-toolkit.googlecode.com/svn/trunk@949 8db76d5a-ed1c-0410-87a9-c151d255dfc7
diff --git a/user/src/com/google/gwt/user/client/ui/StackPanel.java b/user/src/com/google/gwt/user/client/ui/StackPanel.java
index 88b3dbf..e68aa03 100644
--- a/user/src/com/google/gwt/user/client/ui/StackPanel.java
+++ b/user/src/com/google/gwt/user/client/ui/StackPanel.java
@@ -1,12 +1,12 @@
 /*
- * Copyright 2006 Google Inc.
- * 
+ * Copyright 2007 Google Inc.
+ *
  * Licensed under the Apache License, Version 2.0 (the "License"); you may not
  * use this file except in compliance with the License. You may obtain a copy of
  * the License at
- * 
+ *
  * http://www.apache.org/licenses/LICENSE-2.0
- * 
+ *
  * Unless required by applicable law or agreed to in writing, software
  * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
  * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
@@ -59,7 +59,7 @@
 
   /**
    * Adds a new child with the given widget.
-   * 
+   *
    * @param w the widget to be added
    */
   public void add(Widget w) {
@@ -75,6 +75,7 @@
     DOM.appendChild(tr, td);
     setStyleName(td, "gwt-StackPanelItem", true);
     DOM.setElementPropertyInt(td, "__index", index);
+    DOM.setElementPropertyInt(td, "__owner", hashCode());
     DOM.setElementProperty(td, "height", "1px");
 
     tr = DOM.createTR();
@@ -94,7 +95,7 @@
 
   /**
    * Adds a new child with the given widget and header.
-   * 
+   *
    * @param w the widget to be added
    * @param stackText the header text associated with this widget
    */
@@ -105,7 +106,7 @@
   /**
    * Adds a new child with the given widget and header, optionally interpreting
    * the header as HTML.
-   * 
+   *
    * @param w the widget to be added
    * @param stackText the header text associated with this widget
    * @param asHTML <code>true</code> to treat the specified text as HTML
@@ -117,7 +118,7 @@
 
   /**
    * Gets the currently selected child index.
-   * 
+   *
    * @return selected child
    */
   public int getSelectedIndex() {
@@ -138,9 +139,12 @@
 
   public void onBrowserEvent(Event event) {
     if (DOM.eventGetType(event) == Event.ONCLICK) {
-      int index = getDividerIndex(DOM.eventGetTarget(event));
-      if (index != -1) {
-        showStack(index);
+      Element target = DOM.eventGetTarget(event);
+      if (isDividerOwn(target)) {
+        int index = getDividerIndex(target);
+        if (index != -1) {
+          showStack(index);
+        }
       }
     }
   }
@@ -155,7 +159,7 @@
 
   /**
    * Sets the text associated with a child by its index.
-   * 
+   *
    * @param index the index of the child whose text is to be set
    * @param text the text to be associated with it
    */
@@ -165,7 +169,7 @@
 
   /**
    * Sets the text associated with a child by its index.
-   * 
+   *
    * @param index the index of the child whose text is to be set
    * @param text the text to be associated with it
    * @param asHTML <code>true</code> to treat the specified text as HTML
@@ -185,7 +189,7 @@
 
   /**
    * Shows the widget at the specified child index.
-   * 
+   *
    * @param index the index of the child to be shown
    */
   public void showStack(int index) {
@@ -214,6 +218,18 @@
     return -1;
   }
 
+  /**
+   * In the case of nested StackPanels, it's necessary to tell if a
+   * particular StackPanel owns the target of a click before responding to it.
+   * @param elem The Element to examine
+   * @return <code>true</code> iff the Element one to which the StackPanel
+   *           should respond.
+   */
+  private boolean isDividerOwn(Element elem) {
+    int owner = DOM.getElementPropertyInt(elem, "__owner");
+    return owner == hashCode();
+  }
+
   private boolean remove(Widget child, int index) {
     if (child.getParent() != this) {
       return false;