it("should close and return to the host editor", function () {
     var inlineDoc = SpecRunnerUtils.createMockDocument("div{}\n.foo{}\n");
     
     var mockRanges = [
         {
             document: inlineDoc,
             name: "div",
             lineStart: 0,
             lineEnd: 0
         }
     ];
     
     inlineEditor = new MultiRangeInlineEditor(mockRanges);
     inlineEditor.load(hostEditor);
     
     // add widget directly, bypass _openInlineWidget
     hostEditor.addInlineWidget({line: 0, ch: 0}, inlineEditor);
     
     // verify it was added
     expect(hostEditor.hasFocus()).toBe(false);
     expect(hostEditor.getInlineWidgets().length).toBe(1);
     
     // close the inline editor directly, should call EditorManager and removeInlineWidget
     inlineEditor.close();
     
     // verify no editors
     expect(hostEditor.getInlineWidgets().length).toBe(0);
     expect(hostEditor.hasFocus()).toBe(true);
 });
 it("should change selection to the next rule", function () {
     var inlineDoc = SpecRunnerUtils.createMockDocument("div{}\n.foo{}\n");
     
     var mockRanges = [
         {
             document: inlineDoc,
             name: "div",
             lineStart: 0,
             lineEnd: 0
         },
         {
             document: inlineDoc,
             name: ".foo",
             lineStart: 1,
             lineEnd: 1
         }
     ];
     
     inlineEditor = new MultiRangeInlineEditor(mockRanges);
     inlineEditor.load(hostEditor);
     inlineEditor._selectNextRange();
     
     var $selection = $(inlineEditor.htmlContent).find(".selection");
     var $ruleListItems = $(inlineEditor.htmlContent).find("li");
     expect($selection.position().top).toBe($($ruleListItems.get(0)).position().top);
 });
 it("should change selection to the previous rule", function () {
     var inlineDoc = SpecRunnerUtils.createMockDocument("div{}\n.foo{}\n");
     
     var mockRanges = [
         {
             document: inlineDoc,
             name: "div",
             lineStart: 0,
             lineEnd: 0
         },
         {
             document: inlineDoc,
             name: ".foo",
             lineStart: 1,
             lineEnd: 1
         }
     ];
     
     inlineEditor = new MultiRangeInlineEditor(mockRanges);
     inlineEditor.load(hostEditor);
     
     // select .foo
     inlineEditor.setSelectedIndex(1);
     
     // verify selection moves
     var $selection = $(inlineEditor.htmlContent).find(".selection");
     var $ruleListItems = $(inlineEditor.htmlContent).find("li");
     expect($selection.position().top).toBe($($ruleListItems.get(1)).position().top);
     
     // select div
     inlineEditor._selectPreviousRange();
     
     // verify selection moves again
     expect($selection.position().top).toBe($($ruleListItems.get(0)).position().top);
 });
            it("should contain a rule list widget displaying info for each rule", function () {
                var inlineDoc = SpecRunnerUtils.createMockDocument("div{}\n.foo{}\n"),
                    inlineDocName = inlineDoc.file.name;
                
                var mockRanges = [
                    {
                        document: inlineDoc,
                        name: "div",
                        lineStart: 0,
                        lineEnd: 0
                    },
                    {
                        document: inlineDoc,
                        name: ".foo",
                        lineStart: 1,
                        lineEnd: 1
                    }
                ];
                
                inlineEditor = new MultiRangeInlineEditor(mockRanges);
                inlineEditor.load(hostEditor);
                
                var $ruleListItems = getRuleListItems();
                expectListItem($ruleListItems.eq(0), "div", inlineDocName, 1);
                expectListItem($ruleListItems.eq(1), ".foo", inlineDocName, 2);

                // Messages div should be hidden, editor holder should have a child editor.
                expect(inlineEditor.$htmlContent.find(".inline-editor-message").length).toBe(0);
                expect(inlineEditor.$htmlContent.find(".inline-editor-holder").children().length).toBe(1);
                
                // Rule list should be visible.
                expect(inlineEditor.$htmlContent.find(".related-container").length).toBe(1);
            });
 it("should contain a rule list widget displaying info for each rule", function () {
     var inlineDoc = SpecRunnerUtils.createMockDocument("div{}\n.foo{}\n"),
         inlineDocName = inlineDoc.file.name;
     
     var mockRanges = [
         {
             document: inlineDoc,
             name: "div",
             lineStart: 0,
             lineEnd: 0
         },
         {
             document: inlineDoc,
             name: ".foo",
             lineStart: 1,
             lineEnd: 1
         }
     ];
     
     inlineEditor = new MultiRangeInlineEditor(mockRanges);
     inlineEditor.load(hostEditor);
     
     var $ruleListItems = $(inlineEditor.htmlContent).find("li");
     expect($($ruleListItems.get(0)).text()).toBe("div — " + inlineDocName + " : 1");
     expect($($ruleListItems.get(1)).text()).toBe(".foo — " + inlineDocName + " : 2");
 });
 it("should retreive the selected rule", function () {
     var inlineDoc = SpecRunnerUtils.createMockDocument("div{}\n.foo{}\n");
     
     var mockRanges = [
         {
             document: inlineDoc,
             name: "div",
             lineStart: 0,
             lineEnd: 0
         },
         {
             document: inlineDoc,
             name: ".foo",
             lineStart: 1,
             lineEnd: 1
         }
     ];
     
     inlineEditor = new MultiRangeInlineEditor(mockRanges);
     inlineEditor.load(hostEditor);
     
     // "div" rule should be selected by default
     expectResultItemToEqual(inlineEditor._getSelectedRange(), mockRanges[0]);
     
     // select ".foo" rule - should be next
     inlineEditor._selectNextRange();
     expectResultItemToEqual(inlineEditor._getSelectedRange(), mockRanges[1]);
 });
Example #7
0
 .done(function (rules) {
     if (rules && rules.length > 0) {
         var cssInlineEditor = new MultiRangeInlineEditor(rules);
         cssInlineEditor.load(hostEditor);
         
         result.resolve(cssInlineEditor);
     } else {
         // No matching rules were found.
         result.reject();
     }
 })
Example #8
0
            .done(function (rules) {
                var inlineEditorDeferred = new $.Deferred();
                cssInlineEditor = new MultiRangeInlineEditor.MultiRangeInlineEditor(CSSUtils.consolidateRules(rules),
                                                                                    _getNoRulesMsg, CSSUtils.getRangeSelectors);
                cssInlineEditor.load(hostEditor);
                cssInlineEditor.$htmlContent
                    .on("focusin", _updateCommands)
                    .on("focusout", _updateCommands);
                $(cssInlineEditor).on("add", function () {
                    inlineEditorDeferred.resolve();
                });
                $(cssInlineEditor).on("close", function () {
                    _closeDropdown();
                });

                var $header = $(".inline-editor-header", cssInlineEditor.$htmlContent);
                $newRuleButton = $("<button class='stylesheet-button btn btn-mini disabled'/>")
                    .text(Strings.BUTTON_NEW_RULE)
                    .on("click", _handleNewRuleClick);
                $header.append($newRuleButton);
                _newRuleHandlers.push({inlineEditor: cssInlineEditor, handler: _handleNewRuleClick});
                
                result.resolve(cssInlineEditor);

                // Now that dialog has been built, collect list of stylesheets
                var stylesheetsPromise = _getCSSFilesInProject();
                
                // After both the stylesheets are loaded and the inline editor has been added to the DOM,
                // update the UI accordingly. (Those can happen in either order, so we need to wait for both.)
                // Note that the stylesheetsPromise needs to be passed first in order for the fileInfos to be
                // properly passed to the handler, since $.when() passes the results in order of the argument
                // list.
                $.when(stylesheetsPromise, inlineEditorDeferred.promise())
                    .done(function (fileInfos) {
                        cssFileInfos = _prepFileList(fileInfos);
                        
                        // "New Rule" button is disabled by default and gets enabled
                        // here if there are any stylesheets in project
                        if (cssFileInfos.length > 0) {
                            $newRuleButton.removeClass("disabled");
                            if (!rules.length) {
                                // Force focus to the button so the user can create a new rule from the keyboard.
                                $newRuleButton.focus();
                            }
                        }
                        if (cssFileInfos.length > 1) {
                            $newRuleButton.addClass("btn-dropdown");
                        }
                        
                        _updateCommands();
                    });
            })
 it("should load a single rule and initialize htmlContent and editor", function () {
     var inlineDoc = SpecRunnerUtils.createMockDocument("inlineDoc\nstartLine\nendLine\n");
     var mockRange = {
         document: inlineDoc,
         lineStart: 1,
         lineEnd: 2
     };
     
     inlineEditor = new MultiRangeInlineEditor([mockRange]);
     inlineEditor.load(hostEditor);
     
     expect(inlineEditor.editors.length).toBe(1);
     expect(inlineEditor.editors[0].document).toBe(inlineDoc);
 });
 it("should be empty if no ranges are specified", function () {
     inlineEditor = new MultiRangeInlineEditor([]);
     inlineEditor.load(hostEditor);
     
     // There are no ranges to select.
     expect(inlineEditor._selectedRangeIndex).toBe(-1);
     expect(inlineEditor.editor).toBeNull();
     
     // Messages div should be visible, editors div should have no child editor.
     expect(inlineEditor.$htmlContent.find(".inline-editor-message").length).toBe(1);
     expect(inlineEditor.$htmlContent.find(".inline-editor-holder").children().length).toBe(0);
     
     // Rule list should be invisible.
     expect(inlineEditor.$htmlContent.find(".related-container").length).toBe(0);
 });
 it("should show the rule list if a range is added when only one range existed before", function () {
     var doc = SpecRunnerUtils.createMockDocument("div{}\n.foo{}\n"),
         mockRanges = [
             {
                 document: doc,
                 name: "div",
                 lineStart: 0,
                 lineEnd: 0
             }
         ];
     
     inlineEditor = new MultiRangeInlineEditor(mockRanges);
     inlineEditor.load(hostEditor);
     expect(inlineEditor.$htmlContent.find(".related-container").length).toBe(0);
     
     inlineEditor.addAndSelectRange(".foo", doc, 1, 1);
     expect(inlineEditor.$htmlContent.find(".related-container").length).toBe(1);
 });
 function setupNextPrevTest(initialSelectedIndex, collapseA, collapseB, collapseC) {
     var docA = SpecRunnerUtils.createMockDocument(".aaa{}\n",           "css", "/a.css"),
         docB = SpecRunnerUtils.createMockDocument(".bbb1{}\n.bbb2{}\n", "css", "/b.css"),
         docC = SpecRunnerUtils.createMockDocument(".ccc{}\n",           "css", "/c.css"),
         mockRanges = [
             {
                 document: docA,
                 name: ".aaa",
                 lineStart: 0,
                 lineEnd: 0
             },
             {
                 document: docB,
                 name: ".bbb1",
                 lineStart: 0,
                 lineEnd: 0
             },
             {
                 document: docB,
                 name: ".bbb2",
                 lineStart: 1,
                 lineEnd: 1
             },
             {
                 document: docC,
                 name: ".ccc",
                 lineStart: 0,
                 lineEnd: 0
             }
         ];
     
     inlineEditor = new MultiRangeInlineEditor(mockRanges);
     inlineEditor.load(hostEditor);
     
     inlineEditor.setSelectedIndex(initialSelectedIndex);
     
     var $ruleListSections = getRuleListSections();
     if (collapseA) { $ruleListSections.eq(0).click(); }
     if (collapseB) { $ruleListSections.eq(1).click(); }
     if (collapseC) { $ruleListSections.eq(2).click(); }
     
     // Selected index the testcase wanted shouldn't be affected by collapsing
     expect(inlineEditor._selectedRangeIndex).toBe(initialSelectedIndex);
 }
 it("should add a new range at proper sorted pos if there are no other ranges from the same doc", function () {
     var doc1 = SpecRunnerUtils.createMockDocument("div{}\n.foo{}\n", "css", "/a.css"),
         doc2 = SpecRunnerUtils.createMockDocument("#bar{}\n",        "css", "/b.css"),
         mockRanges = [
             {
                 document: doc1,
                 name: "div",
                 lineStart: 0,
                 lineEnd: 0
             },
             {
                 document: doc1,
                 name: ".foo",
                 lineStart: 1,
                 lineEnd: 1
             }
         ];
     
     inlineEditor = new MultiRangeInlineEditor(mockRanges);
     inlineEditor.load(hostEditor);
     
     expect(getRuleListSections().length).toBe(1);
     
     inlineEditor.addAndSelectRange("#bar", doc2, 0, 0);
     
     expect(getRuleListSections().length).toBe(2);  // verify section header created
     
     var newRanges = inlineEditor._getRanges();
     expect(newRanges.length).toBe(3);
     expect(inlineEditor._getSelectedRange()).toBe(newRanges[2]);
     expectResultItemToEqual(newRanges[0], mockRanges[0]);
     expectResultItemToEqual(newRanges[1], mockRanges[1]);
     expectResultItemToEqual(newRanges[2], {
         document: doc2,
         name: "#bar",
         lineStart: 0,
         lineEnd: 0
     });
     
     expect(inlineEditor.editor.document).toBe(doc2);
     expect(inlineEditor.editor.getFirstVisibleLine()).toBe(0);
     expect(inlineEditor.editor.getLastVisibleLine()).toBe(0);
 });
            it("should load a single rule and initialize htmlContent and editor", function () {
                var inlineDoc = SpecRunnerUtils.createMockDocument("inlineDoc\nstartLine\nendLine\n");
                var mockRange = {
                    document: inlineDoc,
                    lineStart: 1,
                    lineEnd: 2
                };
                
                inlineEditor = new MultiRangeInlineEditor([mockRange]);
                inlineEditor.load(hostEditor);
                
                expect(inlineEditor.editor).toBeTruthy();
                expect(inlineEditor.editor.document).toBe(inlineDoc);

                // Messages div should be hidden, editor holder should have a child editor.
                expect(inlineEditor.$htmlContent.find(".inline-editor-message").length).toBe(0);
                expect(inlineEditor.$htmlContent.find(".inline-editor-holder").children().length).toBe(1);
                
                // Rule list should be hidden with only one rule.
                expect(inlineEditor.$htmlContent.find(".related-container").length).toBe(0);
            });
Example #15
0
            .done(function (rules) {
                cssInlineEditor = new MultiRangeInlineEditor(CSSUtils.consolidateRules(rules) || [], _getNoRulesMsg, CSSUtils.getRangeSelectors);
                cssInlineEditor.load(hostEditor);

                var $header = $(".inline-editor-header", cssInlineEditor.$htmlContent);
                $newRuleButton = $("<button class='stylesheet-button btn btn-mini disabled'/>")
                    .text(Strings.BUTTON_NEW_RULE)
                    .on("click", function (e) {
                        if (!$newRuleButton.hasClass("disabled")) {
                            if (cssFileInfos.length === 1) {
                                // Just go ahead and create the rule.
                                _addRule(selectorName, cssInlineEditor, cssFileInfos[0].fullPath);
                            } else if ($dropdown) {
                                _closeDropdown();
                            } else {
                                _showDropdown();
                            }
                        }
                        e.stopPropagation();
                    });
                $header.append($newRuleButton);
                
                result.resolve(cssInlineEditor);

                // Now that dialog has been built, collect list of stylesheets
                FileIndexManager.getFileInfoList("css")
                    .done(function (fileInfos) {
                        cssFileInfos = fileInfos;
                        
                        // "New Rule" button is disabled by default and gets enabled
                        // here if there are any stylesheets in project
                        if (cssFileInfos.length > 0) {
                            $newRuleButton.removeClass("disabled");
                        }
                        if (cssFileInfos.length > 1) {
                            $newRuleButton.addClass("btn-dropdown");
                        }
                    });
            })
 it("should show multiple documents in sorted order", function () {
     var docZ = SpecRunnerUtils.createMockDocument("div{}\n.foo{}\n", "css", "/zzz.css"),
         docA = SpecRunnerUtils.createMockDocument("#bar{}\n",        "css", "/aaa.css"),
         mockRanges = [
             {
                 document: docZ,
                 name: "div",
                 lineStart: 0,
                 lineEnd: 0
             },
             {
                 document: docA,
                 name: "#bar",
                 lineStart: 0,
                 lineEnd: 0
             }
         ];
     
     inlineEditor = new MultiRangeInlineEditor(mockRanges);
     inlineEditor.load(hostEditor);
     
     var displayedRanges = inlineEditor._getRanges();
     expect(displayedRanges.length).toBe(2);
     expectResultItemToEqual(displayedRanges[0], mockRanges[1]);
     expectResultItemToEqual(displayedRanges[1], mockRanges[0]);
     
     var $ruleListItems = getRuleListItems();
     expect($ruleListItems.length).toBe(2);
     expectListItem($ruleListItems.eq(0), "#bar", "aaa.css", 1);
     expectListItem($ruleListItems.eq(1), "div", "zzz.css", 1);
     
     var $ruleListSections = getRuleListSections();
     expect($ruleListSections.length).toBe(2);
     expect($ruleListSections.eq(0).text()).toBe("aaa.css (1)");
     expect($ruleListSections.eq(1).text()).toBe("zzz.css (1)");
     
     expect(inlineEditor._getSelectedRange()).toBe(displayedRanges[0]);
     expect(inlineEditor.editor.document).toBe(docA);
 });
 it("should add a new range after other ranges from the same doc, then select it", function () {
     var doc1 = SpecRunnerUtils.createMockDocument("div{}\n.foo{}\n"),
         doc2 = SpecRunnerUtils.createMockDocument("#bar{}\n"),
         mockRanges = [
             {
                 document: doc1,
                 name: "div",
                 lineStart: 0,
                 lineEnd: 0
             },
             {
                 document: doc2,
                 name: "#bar",
                 lineStart: 0,
                 lineEnd: 0
             }
         ];
     
     inlineEditor = new MultiRangeInlineEditor(mockRanges);
     inlineEditor.load(hostEditor);
     
     inlineEditor.addAndSelectRange(".foo", doc1, 1, 1);
     
     var newRanges = inlineEditor._getRanges();
     expect(newRanges.length).toBe(3);
     expect(inlineEditor._getSelectedRange()).toBe(newRanges[1]);
     expectResultItemToEqual(newRanges[0], mockRanges[0]);
     expectResultItemToEqual(newRanges[1], {
         document: doc1,
         name: ".foo",
         lineStart: 1,
         lineEnd: 1
     });
     expectResultItemToEqual(newRanges[2], mockRanges[1]);
     
     expect(inlineEditor.editor.document).toBe(doc1);
     expect(inlineEditor.editor.getFirstVisibleLine()).toBe(1);
     expect(inlineEditor.editor.getLastVisibleLine()).toBe(1);
 });
 it("should auto-expand collapsed section when adding new range to it", function () {
     var doc1 = SpecRunnerUtils.createMockDocument("div{}\n", "css", "/a.css"),
         doc2 = SpecRunnerUtils.createMockDocument("#bar{}\n.foo{}\n",        "css", "/b.css"),
         mockRanges = [
             {
                 document: doc1,
                 name: "div",
                 lineStart: 0,
                 lineEnd: 0
             },
             {
                 document: doc2,
                 name: "#bar",
                 lineStart: 0,
                 lineEnd: 0
             }
         ];
     
     inlineEditor = new MultiRangeInlineEditor(mockRanges);
     inlineEditor.load(hostEditor);
     
     var $ruleListSections = getRuleListSections();
     $ruleListSections.eq(1).click(); // collapse doc2 section
     expect($ruleListSections.eq(0).find(".disclosure-triangle.expanded").length).toBe(1);  // verify doc1 section still expanded
     expect($ruleListSections.eq(1).find(".disclosure-triangle:not(.expanded)").length).toBe(1); // verify doc2 section now collapsed
     
     inlineEditor.addAndSelectRange(".foo", doc2, 1, 1); // add new item to doc2 section
     
     var newRanges = inlineEditor._getRanges();
     expect(newRanges.length).toBe(3);
     expect(inlineEditor._getSelectedRange()).toBe(newRanges[2]);  // new range should be 3rd in list & be selected
     expect(inlineEditor.editor.document).toBe(doc2);
     
     $ruleListSections = getRuleListSections();
     expect($ruleListSections.length).toBe(2);  // still just 2 sections
     expect($ruleListSections.eq(0).find(".disclosure-triangle.expanded").length).toBe(1);  // doc1 section still expanded
     expect($ruleListSections.eq(1).find(".disclosure-triangle.expanded").length).toBe(1);  // doc2 section now collapsed also
 });
 it("should retreive all rules", function () {
     var inlineDoc = SpecRunnerUtils.createMockDocument("div{}\n.foo{}\n");
     var mockRanges = [
         {
             document: inlineDoc,
             name: "div",
             lineStart: 0,
             lineEnd: 0
         },
         {
             document: inlineDoc,
             name: ".foo",
             lineStart: 1,
             lineEnd: 1
         }
     ];
     
     inlineEditor = new MultiRangeInlineEditor(mockRanges);
     
     expect(inlineEditor._getRanges().length).toEqual(mockRanges.length);
     expectResultItemToEqual(inlineEditor._getRanges()[0], mockRanges[0]);
     expectResultItemToEqual(inlineEditor._getRanges()[1], mockRanges[1]);
 });
 it("should properly refresh the editor if the range is inserted at the currently selected index", function () {
     var doc1 = SpecRunnerUtils.createMockDocument("div{}\n.foo{}\n", "css", "/a.css"),
         doc2 = SpecRunnerUtils.createMockDocument("#bar{}\n",        "css", "/b.css"),
         mockRanges = [
             {
                 document: doc1,
                 name: "div",
                 lineStart: 0,
                 lineEnd: 0
             },
             {
                 document: doc2,
                 name: "#bar",
                 lineStart: 0,
                 lineEnd: 0
             }
         ];
     
     inlineEditor = new MultiRangeInlineEditor(mockRanges);
     inlineEditor.load(hostEditor);
     
     inlineEditor.setSelectedIndex(1);
     inlineEditor.addAndSelectRange(".foo", doc1, 1, 1);
     
     var newRanges = inlineEditor._getRanges();
     expect(newRanges.length).toBe(3);
     expect(inlineEditor._getSelectedRange()).toBe(newRanges[1]);
     expectResultItemToEqual(newRanges[0], mockRanges[0]);
     expectResultItemToEqual(newRanges[1], {
         document: doc1,
         name: ".foo",
         lineStart: 1,
         lineEnd: 1
     });
     expectResultItemToEqual(newRanges[2], mockRanges[1]);
     
     expect(inlineEditor.editor.document).toBe(doc1);
     expect(inlineEditor.editor.getFirstVisibleLine()).toBe(1);
     expect(inlineEditor.editor.getLastVisibleLine()).toBe(1);
 });
Example #21
0
            .done(function (rules) {
                var inlineEditorDeferred = new $.Deferred();
                cssInlineEditor = new MultiRangeInlineEditor.MultiRangeInlineEditor(CSSUtils.consolidateRules(rules),
                                                                                    _getNoRulesMsg, CSSUtils.getRangeSelectors);
                cssInlineEditor.load(hostEditor);
                cssInlineEditor.$htmlContent
                    .on("focusin", _updateCommands)
                    .on("focusout", _updateCommands);
                $(cssInlineEditor).on("add", function () {
                    inlineEditorDeferred.resolve();
                });
                $(cssInlineEditor).on("close", function () {
                    newRuleButton.closeDropdown();
                    $(hostEditor).off("scroll", _onHostEditorScroll);
                });

                var $header = $(".inline-editor-header", cssInlineEditor.$htmlContent);
                newRuleButton = new DropdownButton(Strings.BUTTON_NEW_RULE, [], _stylesheetListRenderer); // actual item list populated later, below
                newRuleButton.$button.addClass("disabled");  // disabled until list is known
                newRuleButton.$button.addClass("btn-mini stylesheet-button");
                $header.append(newRuleButton.$button);
                _newRuleHandlers.push({inlineEditor: cssInlineEditor, handler: _handleNewRuleClick});
                
                $(hostEditor).on("scroll", _onHostEditorScroll);
                
                result.resolve(cssInlineEditor);
                

                // Now that dialog has been built, collect list of stylesheets
                var stylesheetsPromise = _getCSSFilesInProject();
                
                // After both the stylesheets are loaded and the inline editor has been added to the DOM,
                // update the UI accordingly. (Those can happen in either order, so we need to wait for both.)
                // Note that the stylesheetsPromise needs to be passed first in order for the fileInfos to be
                // properly passed to the handler, since $.when() passes the results in order of the argument
                // list.
                $.when(stylesheetsPromise, inlineEditorDeferred.promise())
                    .done(function (fileInfos) {
                        cssFileInfos = _prepFileList(fileInfos);
                        
                        // "New Rule" button is disabled by default and gets enabled
                        // here if there are any stylesheets in project
                        if (cssFileInfos.length > 0) {
                            newRuleButton.$button.removeClass("disabled");
                            if (!rules.length) {
                                // Force focus to the button so the user can create a new rule from the keyboard.
                                newRuleButton.$button.focus();
                            }
                            
                            if (cssFileInfos.length === 1) {
                                // Make it look & feel like a plain button in this case
                                newRuleButton.$button.removeClass("btn-dropdown");
                                newRuleButton.$button.on("click", _handleNewRuleClick);
                            } else {
                                // Fill out remaining dropdown attributes otherwise
                                newRuleButton.items = cssFileInfos;
                                $(newRuleButton).on("select", _onDropdownSelect);
                            }
                        }
                        
                        _updateCommands();
                    });
            })