Index: /Users/colin/Documents/fluid_repos/components/src/webapp/fluid-components/js/fluid/Fluid.js
===================================================================
--- /Users/colin/Documents/fluid_repos/components/src/webapp/fluid-components/js/fluid/Fluid.js	(revision 5176)
+++ /Users/colin/Documents/fluid_repos/components/src/webapp/fluid-components/js/fluid/Fluid.js	(working copy)
@@ -104,6 +104,30 @@
         return obj.jquery ? obj[0] : obj; // Unwrap the element if it's a jQuery.
     };
     
+    /**
+     * Fetches a single container element and returns a jQuery.
+     * 
+     * @param {String||jQuery||Element} container and id specifying the container, a single-element jQuery, or a DOM element
+     * @return a single-element jQuery of container
+     */
+    fluid.container = function (container) {
+        if (!container.jquery && (typeof container === "string")) {
+            container = fluid.utils.jById(container);
+        } else if (container instanceof Element) {
+            container = jQuery(container);
+        }
+        
+        // Throw an exception if we've got more or less than one element.
+        if (!container || container.length !== 1) {
+            throw {
+                name: "NotOne",
+                message: "More than one element was found for the specified container."
+            };
+        }
+        
+        return container;
+    };
+    
     var defaultsStore = {};
     fluid.defaults = function (componentName, defaultsObject) {
         if (arguments.length > 1) {
Index: /Users/colin/Documents/fluid_repos/components/src/webapp/fluid-components/js/fluid/InlineEdit.js
===================================================================
--- /Users/colin/Documents/fluid_repos/components/src/webapp/fluid-components/js/fluid/InlineEdit.js	(revision 5176)
+++ /Users/colin/Documents/fluid_repos/components/src/webapp/fluid-components/js/fluid/InlineEdit.js	(working copy)
@@ -111,22 +111,29 @@
     }
     
     function aria(text, editContainer) {
-        // Need to add ARIA roles and states.
+        text.ariaRole("button");
     }
     
-    fluid.InlineEdit = function (componentContainerId, options) {
+    var mixDefaults = function(instance, defaults, options) {
+        instance.selectors = $.extend({}, defaults.selectors, options.selectors);
+        instance.styles = $.extend({}, defaults.styles, options.styles);
+        instance.paddings = $.extend({}, defaults.paddings, options.paddings);
+        instance.finishedEditing = options.finishedEditing || function () {};    
+    };
+    
+    var bindToDom = function (instance, container) {
+        // Bind to the DOM.
+        instance.container = fluid.container(container);
+        instance.text = $(instance.selectors.text, instance.container);
+        instance.editContainer = $(instance.selectors.editContainer, instance.container);
+        instance.editField = $(instance.selectors.edit, instance.editContainer);
+    };
+    
+    fluid.InlineEdit = function (componentContainer, options) {
         // Mix in the user's configuration options.
         options = options || {};
-        var selectors = $.extend({}, this.defaults.selectors, options.selectors);
-        this.styles = $.extend({}, this.defaults.styles, options.styles);
-        this.paddings = $.extend({}, this.defaults.paddings, options.paddings);
-		this.finishedEditing = options.finishedEditing || function () {};
-        
-        // Bind to the DOM.
-        this.container = fluid.utils.jById(componentContainerId);
-        this.text = $(selectors.text, this.container);
-        this.editContainer = $(selectors.editContainer, this.container);
-        this.editField = $(selectors.edit, this.editContainer);
+        mixDefaults(this, this.defaults, options);
+        bindToDom(this, componentContainer);
         
         // Add event handlers.
         mouse(this.text, this.editContainer, this.editField, this.styles, this.paddings, this.finishedEditing);
@@ -141,7 +148,6 @@
         this.editContainer.hide();
     };
     
-    // Seems a bit strange that we put edit and finish on the prototype but internally we just use the private functions
     fluid.InlineEdit.prototype.edit = function () {
         edit(this.text, this.editContainer, this.editField, this.styles.invitation, this.styles.focus, this.paddings);
     };
@@ -167,5 +173,34 @@
 			minimum: 80
 		}
     };
+    
+    /**
+     * A set of inline edit fields.
+     */
+    var setupInlineEdits = function  (editables, options) {
+        var editors = [];
+        editables.each(function (idx, editable) {
+            editors.push(new fluid.InlineEdit(jQuery(editable), options));
+        });
         
+        return editors;
+    };
+
+    fluid.inlineEdits = function (componentContainerId, options) {
+        var that = {};
+        options = options || {};
+        that.selectors = $.extend({}, fluid.defaults("inlineEdits").selectors, options.selectors);
+        
+        // Bind to the DOM.
+        var container = fluid.utils.jById(componentContainerId);
+        var editables = $(that.selectors.editables, container);
+        
+        return setupInlineEdits(editables, options);
+    };
+    
+    fluid.defaults("inlineEdits", {
+        selectors: {
+            editables: ".inlineEditable"
+        }
+    });
 })(jQuery, fluid);
Index: /Users/colin/Documents/fluid_repos/components/src/webapp/sample-code/inline-edit/announcements/announcements.html
===================================================================
--- /Users/colin/Documents/fluid_repos/components/src/webapp/sample-code/inline-edit/announcements/announcements.html	(revision 5176)
+++ /Users/colin/Documents/fluid_repos/components/src/webapp/sample-code/inline-edit/announcements/announcements.html	(working copy)
@@ -220,7 +220,7 @@
                 </div>
             </div>
             <form name="announcementListForm" action="http://build.fluidproject.org/portal/tool/ann?panel=Main" method="post">
-                <table class="listHier" summary="Table contains a list of announcements. It is five or six columns wide and each row contains a single announcement. Column one indicates if the announcement has an attachment, column two contains the title of the announcement, column three has the name of the author, column four shows the recipient, column five contains the date and time of publication, column six, if present, contains a checkbox - selecting it will mean you want to remove this announcement. The following row will contain announcement text if site owner has set it to be so." border="0" cellspacing="0">
+                <table id="announcements" class="listHier" summary="Table contains a list of announcements. It is five or six columns wide and each row contains a single announcement. Column one indicates if the announcement has an attachment, column two contains the title of the announcement, column three has the name of the author, column four shows the recipient, column five contains the date and time of publication, column six, if present, contains a checkbox - selecting it will mean you want to remove this announcement. The following row will contain announcement text if site owner has set it to be so." border="0" cellspacing="0">
                     <tbody>
                         <tr>
                             <th id="attach" class="attach">
@@ -245,7 +245,7 @@
                             <td headers="attach" class="attach">
                                 &nbsp;
                             </td>
-                            <td headers="subject" id="announcement1">
+                            <td headers="subject" class="inlineEditable">
                                 <span class="text">Lecture Room Change</span>
                                 <div class="editContainer">
                                     <input type="text" class="edit" />
@@ -271,7 +271,7 @@
                             <td headers="attach" class="attach">
                                 &nbsp;
                             </td>
-                            <td headers="subject" id="announcement2">
+                            <td headers="subject" class="inlineEditable">
                                 <span class="text">Reading for Tuesday's Lab</span>
                                 <div class="editContainer">
                                     <input type="text" class="edit" />
@@ -297,7 +297,7 @@
                             <td headers="attach" class="attach">
                                 &nbsp;
                             </td>
-                            <td headers="subject" id="announcement3">
+                            <td headers="subject" class="inlineEditable">
                                 <span class="text">DNA Polymorphism Exam on Thursday</span>
                                 <div class="editContainer">
                                     <input type="text" class="edit" />
@@ -326,9 +326,12 @@
                 </p>
 
                 <script type="text/javascript">
+                    fluid.inlineEdits("announcements");
+                    /*
                     new fluid.InlineEdit("announcement1");
                     new fluid.InlineEdit("announcement2");
 					new fluid.InlineEdit("announcement3");
+					*/
                 </script>
 
             </form>
Index: /Users/colin/Documents/fluid_repos/components/src/webapp/tests/fluid-tests/FluidJS-test.html
===================================================================
--- /Users/colin/Documents/fluid_repos/components/src/webapp/tests/fluid-tests/FluidJS-test.html	(revision 5176)
+++ /Users/colin/Documents/fluid_repos/components/src/webapp/tests/fluid-tests/FluidJS-test.html	(working copy)
@@ -25,7 +25,7 @@
     <ol id="tests"></ol>
 
     <!-- Test HTML -->
-    <div id="main" style="display:none;">
+    <div id="main" style="display:none;" class="container">
 
 	    <ul id="pager-top" class="pager-top">
    	        <li id="top1" class="page-link"><a href="#" id="page-link-1">1</a></li>
@@ -37,5 +37,9 @@
 
      </div>
 
+    <div id="notmain" class="container">
+        
+    </div>
+   
 	</body>
 </html>
Index: /Users/colin/Documents/fluid_repos/components/src/webapp/tests/fluid-tests/InlineEdit-test.html
===================================================================
--- /Users/colin/Documents/fluid_repos/components/src/webapp/tests/fluid-tests/InlineEdit-test.html	(revision 5176)
+++ /Users/colin/Documents/fluid_repos/components/src/webapp/tests/fluid-tests/InlineEdit-test.html	(working copy)
@@ -31,7 +31,7 @@
       <div id="main">
 
         <!-- This is the test data -->
-	    <form id="inline-edit" action="#">
+	    <form id="inline-edit" action="#" class="inlineEditable">
 	        <div id="display" class="text">Click me to edit...</div>
             <div id="edit-container" class="editContainer">
                 <input id="edit" type="text" class="edit" value="this is the hidden text for the first editor" />
@@ -38,10 +38,17 @@
             </div>
 	    </form>
         
+        <form id="inline-edit2" action="#" class="inlineEditable">
+	        <div id="display2" class="text">Click me to edit...</div>
+            <div id="edit-container2" class="editContainer">
+                <input id="edit2" type="text" class="edit" value="this is the hidden text for the second editor" />
+            </div>
+	    </form>
+        
 	    <form id="inline-edit-custom" action="#">
 	        <div id="display-custom" class="customText">Click me to edit...</div>
             <div id="edit-container-custom" class="customEditContainer">
-                <input id="edit-custom" type="text" class="customEdit" value="this is the hidden text for the second editor" />
+                <input id="edit-custom" type="text" class="customEdit" value="this is the hidden text for the custom editor" />
             </div>
 	    </form>
       </div>
Index: /Users/colin/Documents/fluid_repos/components/src/webapp/tests/fluid-tests/js/FluidJSTests.js
===================================================================
--- /Users/colin/Documents/fluid_repos/components/src/webapp/tests/fluid-tests/js/FluidJSTests.js	(revision 5176)
+++ /Users/colin/Documents/fluid_repos/components/src/webapp/tests/fluid-tests/js/FluidJSTests.js	(working copy)
@@ -238,6 +238,57 @@
             jqUnit.assertEquals("Ancestor should be 'top1'", "top1", fluid.utils.findAncestor($("#page-link-1"), testFunc).id);
         });
         
+        fluidJSTests.test("Container: bind to an id", function () {
+            // Give it a valid id string.
+            var result = fluid.container("main");
+            jqUnit.assertTrue("One element should be returned when specifying a container id",
+                              1, result.length);
+          
+            // Now try with a invalid string... a CSS selector. container() should only accept ids and single-member jQueries            
+            try {
+                result = fluid.container(".container");
+                jqUnit.ok(false); // We expect to get an exception. If we don't, fail immediately.
+            } catch (e) {
+                jqUnit.assertEquals("The exception should be a NotOne.", "NotOne", e.name);
+            }
+        });
+    
+        fluidJSTests.test("container(): bind to a single jQuery", function() {
+            // Try with a single-item jQuery.
+            var oneContainer = jQuery("#main");
+            var result = fluid.container(oneContainer);
+            jqUnit.assertEquals("If a single-element jQuery is used, it should be immediately returned.",
+                         oneContainer, result);
+             
+            // Now try with a two-element jQuery, which should cause an exception.
+            var twoContainers = jQuery(".container");
+            try {
+                result = fluid.container(twoContainers);
+                jqUnit.ok(false); // We expect to get an exception. If we don't, fail immediately.
+            } catch (e) {
+                jqUnit.assertEquals("The exception should be a NotOne.", "NotOne", e.name);
+            }
+        });
+        
+        fluidJSTests.test("container(): bind to a DOM element", function () {
+            var container = document.getElementById("main");
+            var result = fluid.container(container);
+            jqUnit.assertEquals("If a single DOM element is used, it should be wrapped in a jQuery.",
+                                container, result[0]);
+        });
+        
+        fluidJSTests.test("container(): garbage object", function () {
+            // Random objects should fail.
+            var container = {foo: "bar"};
+
+            try {
+                var result = fluid.container(container);
+                jqUnit.ok(false); // We expect to get an exception. If we don't, fail immediately.
+            } catch (e) {
+                jqUnit.assertEquals("The exception should be a NotOne.", "NotOne", e.name);
+            }
+        });
+        
          
         fluidJSTests.test("Defaults: store and retrieve default values", function () {
             var testDefaults = {
@@ -269,5 +320,4 @@
                               fluid.defaults("timemachine"));
         });
     });
-
 })(jQuery);
Index: /Users/colin/Documents/fluid_repos/components/src/webapp/tests/fluid-tests/js/InlineEditTests.js
===================================================================
--- /Users/colin/Documents/fluid_repos/components/src/webapp/tests/fluid-tests/js/InlineEditTests.js	(revision 5176)
+++ /Users/colin/Documents/fluid_repos/components/src/webapp/tests/fluid-tests/js/InlineEditTests.js	(working copy)
@@ -215,4 +215,52 @@
         jqUnit.assertFalse("Blur saves the edit", edit.text() === display.text());
     });
     
+    // Multiple Inline Editors tests
+    (function () {
+        var inlineEditsSel = "form.inlineEditable";
+        var editor1Sels = {
+            display: "#display",
+            edit: "#edit-container"  
+        };
+        
+        var editor2Sels = {
+            display: "#display2",
+            edit: "#edit-container2"
+        };
+       
+        var instantiateInlineEdits = function () {
+            return fluid.inlineEdits("main", {
+               selectors: {
+                   editables: inlineEditsSel
+               }
+            });
+        };
+        
+        inlineEditTests.test("inlineEdits(): instantiate more than one", function () {
+           jqUnit.expect(1);
+
+           var editors = instantiateInlineEdits();
+           jqUnit.assertEquals("There should be two inline editors on the page.",
+                               2, editors.length);
+        });
+        
+        inlineEditTests.test("inlineEdits(): call to edit affects only one at a time", function () {
+            jqUnit.expect(8);
+            
+            var editors = instantiateInlineEdits();
+            
+            // First check that the displays are shown and the edits are hidden.
+            jqUnit.isVisible("Initially, display field #1 is visible", editor1Sels.display);
+            jqUnit.isVisible("Initially, display field #2 is visible", editor2Sels.display);
+            jqUnit.notVisible("Initially, edit field #1 is hidden", editor1Sels.edit);
+            jqUnit.notVisible("Initially, edit field #2 is hidden", editor2Sels.edit);
+            
+            editors[0].edit();
+            
+            jqUnit.notVisible("Display field #1 should be hidden", editor1Sels.display);
+            jqUnit.isVisible("Edit field #1 should be visible", editor1Sels.edit);
+            jqUnit.isVisible("Display field #2 should be visible", editor2Sels.display);
+            jqUnit.notVisible("Edit field #2 should be hidden", editor2Sels.edit);
+        });
+    })();
 });
\ No newline at end of file
