Bug 1276562 - Hang when inserting a bulleted or numbered list into a contentEditable. r=yzen, a=gchang
authorAlexander Surkov <surkov.alexander@gmail.com>
Tue, 31 May 2016 14:46:31 -0400
changeset 333219 b787be8570fc1a5a91fd6b3ec1c09a9ecdc7cc84
parent 333218 1d0f99529b3109563afb853d45ab26b602718e17
child 333220 12ebcba46956a810bed79613d03e70c432525025
push id6048
push userkmoir@mozilla.com
push dateMon, 06 Jun 2016 19:02:08 +0000
treeherdermozilla-beta@46d72a56c57d [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersyzen, gchang
bugs1276562
milestone48.0a2
Bug 1276562 - Hang when inserting a bulleted or numbered list into a contentEditable. r=yzen, a=gchang
accessible/html/HTMLListAccessible.cpp
accessible/html/HTMLListAccessible.h
accessible/html/HTMLTableAccessible.h
accessible/tests/mochitest/treeupdate/test_list.html
--- a/accessible/html/HTMLListAccessible.cpp
+++ b/accessible/html/HTMLListAccessible.cpp
@@ -87,16 +87,27 @@ HTMLLIAccessible::Bounds() const
 
   nsIntRect bulletRect = mBullet->Bounds();
 
   rect.width += rect.x - bulletRect.x;
   rect.x = bulletRect.x; // Move x coordinate of list item over to cover bullet as well
   return rect;
 }
 
+bool
+HTMLLIAccessible::InsertChildAt(uint32_t aIndex, Accessible* aChild)
+{
+  // Adjust index if there's a bullet.
+  if (mBullet && aIndex == 0 && aChild != mBullet) {
+    return HyperTextAccessible::InsertChildAt(aIndex + 1, aChild);
+  }
+
+  return HyperTextAccessible::InsertChildAt(aIndex, aChild);
+}
+
 ////////////////////////////////////////////////////////////////////////////////
 // HTMLLIAccessible: public
 
 void
 HTMLLIAccessible::UpdateBullet(bool aHasBullet)
 {
   if (aHasBullet == !!mBullet) {
     NS_NOTREACHED("Bullet and accessible are in sync already!");
--- a/accessible/html/HTMLListAccessible.h
+++ b/accessible/html/HTMLListAccessible.h
@@ -48,16 +48,18 @@ public:
   NS_DECL_ISUPPORTS_INHERITED
 
   // Accessible
   virtual void Shutdown() override;
   virtual nsIntRect Bounds() const override;
   virtual a11y::role NativeRole() override;
   virtual uint64_t NativeState() override;
 
+  virtual bool InsertChildAt(uint32_t aIndex, Accessible* aChild) override;
+
   // HTMLLIAccessible
   HTMLListBulletAccessible* Bullet() const { return mBullet; }
   void UpdateBullet(bool aHasBullet);
 
 protected:
   virtual ~HTMLLIAccessible() { }
 
 private:
--- a/accessible/html/HTMLTableAccessible.h
+++ b/accessible/html/HTMLTableAccessible.h
@@ -152,17 +152,17 @@ public:
   // Accessible
   virtual TableAccessible* AsTable() override { return this; }
   virtual void Description(nsString& aDescription) override;
   virtual a11y::role NativeRole() override;
   virtual uint64_t NativeState() override;
   virtual already_AddRefed<nsIPersistentProperties> NativeAttributes() override;
   virtual Relation RelationByType(RelationType aRelationType) override;
 
-  bool InsertChildAt(uint32_t aIndex, Accessible* aChild) override;
+  virtual bool InsertChildAt(uint32_t aIndex, Accessible* aChild) override;
 
 protected:
   virtual ~HTMLTableAccessible() {}
 
   // Accessible
   virtual ENameValueFlag NativeName(nsString& aName) override;
 
   // HTMLTableAccessible
--- a/accessible/tests/mochitest/treeupdate/test_list.html
+++ b/accessible/tests/mochitest/treeupdate/test_list.html
@@ -77,35 +77,60 @@
       this.process = function showProcessor_process()
       {
         this.liNode.style.display = "list-item";
       }
 
       this.onProcessed = function showProcessor_onProcessed()
       {
         testLiAccessibleTree();
+        gSequence.processNext();
+      }
+    };
+
+    function textReplaceProcessor()
+    {
+      this.liNode = getNode("li");
+
+      this.process = function textReplaceProcessor_process()
+      {
+        this.liNode.textContent = "hey";
+      }
+
+      this.onProcessed = function textReplaceProcessor_onProcessed()
+      {
+        var tree = {
+          LISTITEM: [
+            { STATICTEXT: [] },
+            { TEXT_LEAF: [] }
+          ]
+        };
+        testAccessibleTree(this.liNode, tree);
         SimpleTest.finish();
       }
     };
 
     ////////////////////////////////////////////////////////////////////////////
     // Test
 
+    //gA11yEventDumpToConsole = true;
+
     var gSequence = null;
-
     function doTest()
     {
       testLiAccessibleTree();
 
       gSequence = new sequence();
 
       gSequence.append(new hideProcessor(), EVENT_HIDE, getAccessible("li"),
                        "hide HTML li");
       gSequence.append(new showProcessor(), EVENT_SHOW, getNode("li"),
                        "show HTML li");
+      gSequence.append(new textReplaceProcessor(), EVENT_REORDER, getNode("li"),
+                       "change text of HTML li");
 
       gSequence.processNext(); // SimpleTest.finish() will be called in the end
     }
 
     SimpleTest.waitForExplicitFinish();
     addA11yLoadEvent(doTest);
   </script>
 </head>