r3495 committed - merging menu code into autocomplete for 1.8 release, will be split aga...

r3495 committed - merging menu code into autocomplete for 1.8 release, will be split aga...

Revision: 3495
Author: joern.zaefferer
Date: Tue Dec 15 13:13:03 2009
Log: merging menu code into autocomplete for 1.8 release, will be split
again afterwards; added demos for autocomplete, based on visual tests; two
small fixes for autocomplete: cursor:default for the autocomplete-menu and
preventing a stray change-event when the value is < minLength
http://code.google.com/p/jquery-ui/source/detail?r=3495
Added:
/branches/dev/demos/autocomplete
/branches/dev/demos/autocomplete/combobox.html
/branches/dev/demos/autocomplete/default.html
/branches/dev/demos/autocomplete/index.html
/branches/dev/demos/autocomplete/remote-jsonp.html
/branches/dev/demos/autocomplete/remote-with-cache.html
/branches/dev/demos/autocomplete/remote.html
/branches/dev/demos/autocomplete/search.php
Deleted:
/branches/dev/themes/base/ui.menu.css
/branches/dev/ui/jquery.ui.menu.js
Modified:
/branches/dev/demos/index.html
/branches/dev/tests/visual/autocomplete/combobox.html
/branches/dev/tests/visual/autocomplete/default.html
/branches/dev/tests/visual/autocomplete/remote-jsonp.html
/branches/dev/tests/visual/autocomplete/remote-with-cache.html
/branches/dev/tests/visual/autocomplete/remote.html
/branches/dev/tests/visual/menu/contextmenu.html
/branches/dev/tests/visual/menu/default.html
/branches/dev/tests/visual/menu/drilldown.html
/branches/dev/tests/visual/menu/nested.html
/branches/dev/themes/base/ui.autocomplete.css
/branches/dev/themes/base/ui.base.css
/branches/dev/ui/jquery.ui.autocomplete.js
=======================================
--- /dev/null
+++ /branches/dev/demos/autocomplete/combobox.html    Tue Dec 15 13:13:03 2009
@@ -0,0 +1,122 @@
+<!doctype html>
+<html>
+<head>
+    <title>jQuery UI Autocomplete Combobox Demo</title>
+    <link type="text/css" href="../../themes/base/ui.all.css"
rel="stylesheet" />
+    <script type="text/javascript" src="../../jquery-1.3.2.js"></script>
+    <script type="text/javascript" src="../../ui/jquery.ui.core.js"></script>
+    <script type="text/javascript"
src="../../ui/jquery.ui.button.js"></script>
+    <script type="text/javascript"
src="../../ui/jquery.ui.position.js"></script>
+    <script type="text/javascript"
src="../../ui/jquery.ui.autocomplete.js"></script>
+    <link type="text/css" href="../demos.css" rel="stylesheet" />
+    <script type="text/javascript">
+    (function($) {
+        $.widget("ui.selectAutocomplete", {
+            _init: function() {
+                var self = this;
+                var select = this.element.hide();
+                var input = $("<input/>").addClass("ui-widget ui-widget-content
ui-corner-left").insertAfter(select).autocomplete({
+                    source: function(request) {
+                        var matcher = new RegExp(request.term, "i");
+                        return select.children("option").map(function() {
+                            var text = $(this).text();
+                            if (!request.term || matcher.test(text))
+                                return {
+                                    id: $(this).val(),
+                                    label: text.replace(new RegExp("(?![^&;]+;)(?!<[^<>]*)(" +
request.term.replace(/([\^\$\(\)\[\]\{\}\*\.\+\?\|\\])/gi, "\\$1")
+ ")(?![^<>]*>)(?![^&;]+;)", "gi"), "<strong>$1</strong>"),
+                                    result: text
+                                };
+                        });
+                    },
+                    delay: 0,
+                    change: function(e, ui) {
+                        if (!ui.item) {
+                            // remove invalid value, as it didn't match anything
+                            $(this).val("");
+                            return;
+                        }
+                        $(this).focus();
+                        select.val(ui.item.id);
+                        self._trigger("selected", null, {
+                            item: select.find("[value='" + ui.item.id + "']")
+                        });
+
+                    },
+                    minLength: 0
+                });
+                $("<button>&nbsp;</button>")
+                .insertAfter(input)
+                .button({
+                    icons: {
+                        primary: "ui-icon-triangle-1-s"
+                    },
+                    text: false
+                }).removeClass("ui-corner-all")
+                .addClass("ui-corner-right ui-button-icon")
+                .position({
+                    my: "left center",
+                    at: "right center",
+                    of: input,
+                    offset: "-1 0"
+                }).css("top", "")
+                .click(function() {
+                    // close if already visible
+                    // TODO but only if shown by button click
+                    if (input.autocomplete("widget").is(":visible")) {
+                        input.autocomplete("close");
+                        return;
+                    }
+                    // pass empty string as value to search for, displaying all results
+                    input.autocomplete("search", "");
+                    input.focus();
+                });
+            }
+        });
+
+    })(jQuery);
+
+    $(function() {
+        $("select").selectAutocomplete();
+    });
+    </script>
+    <style>
+        /* TODO shouldn't be necessary */
+        .ui-button-icon-only .ui-button-text { padding: 0; }
+    </style>
+</head>
+<body>
+
+<div class="demo">
+
+<div class="ui-widget">
+    <label>Your preferred programming language: </label>
+    <select>
+        <option value="a">asp</option>
+ <option value="c">c</option>
+ <option value="cpp">c++</option>
+ <option value="cf">coldfusion</option>
+ <option value="g">groovy</option>
+ <option value="h">haskell</option>
+ <option value="j">java</option>
+ <option value="js">javascript</option>
+ <option value="p1">pearl</option>
+ <option value="p2">php</option>
+ <option value="p3">python</option>
+ <option value="r">ruby</option>
+ <option value="s">scala</option>
+    </select>
+</div>
+
+</div><!-- End demo -->
+
+<div class="demo-description">
+


+A custom widget built by composition of Autocomplete and Button. You can
either type something into the field to get filtered suggestions based on
your input, or use the button to get the full list of selections.
+




+


+The input is read from an existing select-element for progressive
enhancement, passed to Autocomplete with a customized source-option.
+



+</div><!-- End demo-description -->
+
+</body>
+</html>
=======================================
--- /dev/null
+++ /branches/dev/demos/autocomplete/default.html    Tue Dec 15 13:13:03 2009
@@ -0,0 +1,41 @@
+<!doctype html>
+<html>
+<head>
+    <title>jQuery UI Autocomplete Default Demo</title>
+    <link type="text/css" href="../../themes/base/ui.all.css"
rel="stylesheet" />
+    <script type="text/javascript" src="../../jquery-1.3.2.js"></script>
+    <script type="text/javascript" src="../../ui/jquery.ui.core.js"></script>
+    <script type="text/javascript"
src="../../ui/jquery.ui.position.js"></script>
+    <script type="text/javascript"
src="../../ui/jquery.ui.autocomplete.js"></script>
+    <link type="text/css" href="../demos.css" rel="stylesheet" />
+    <script type="text/javascript">
+    $(function() {
+        var availableTags =
["c++", "java", "php", "coldfusion", "javascript", "asp", "ruby", "python", "c", "scala", "groovy", "haskell", "pearl"];
+        $("#tags").autocomplete({
+            source: availableTags
+        });
+    });
+    </script>
+</head>
+<body>
+
+<div class="demo">
+
+<div class="ui-widget">
+    <label for="tags">Tags: </label>
+    <input class="ui-widget ui-widget-content ui-corner-all" id="tags" />
+</div>
+
+</div><!-- End demo -->
+
+<div class="demo-description">
+


+The Autocomplete widgets provides suggestions while you type into the
field. Here the suggestions are tags for programming languages, give "ja"
(for Java or JavaScript) a try.
+




+


+The datasource is a simple JavaScript array, provided to the widget using
the source-option.
+



+</div><!-- End demo-description -->
+
+</body>
+</html>
=======================================
--- /dev/null
+++ /branches/dev/demos/autocomplete/index.html    Tue Dec 15 13:13:03 2009
@@ -0,0 +1,19 @@
+<!doctype html>
+<html lang="en">
+<head>
+    <title>jQuery UI Autocomplete Demos</title>
+    <link type="text/css" href="../demos.css" rel="stylesheet" />
+</head>
+<body>
+    <div class="demos-nav">
+        <h4>Examples</h4>
+        <ul>
+            <li class="demo-config-on"><a href="default.html">Default
functionality</a></li>
+            <li><a href="remote.html">Remote datasource</a></li>
+            <li><a href="remote-with-cache.html">Remote with caching</a></li>
+            <li><a href="remote-jsonp.html">Remote JSONP datasource</a></li>
+            <li><a href="combobox.html">Combobox</a></li>
+        </ul>
+    </div>
+</body>
+</html>
=======================================
--- /dev/null
+++ /branches/dev/demos/autocomplete/remote-jsonp.html    Tue Dec 15 13:13:03
2009
@@ -0,0 +1,84 @@
+<!doctype html>
+<html>
+<head>
+    <title>jQuery UI Autocomplete Remote JSONP datasource demo</title>
+    <link type="text/css" href="../../themes/base/ui.all.css"
rel="stylesheet" />
+    <script type="text/javascript" src="../../jquery-1.3.2.js"></script>
+    <script type="text/javascript" src="../../ui/jquery.ui.core.js"></script>
+    <script type="text/javascript"
src="../../ui/jquery.ui.position.js"></script>
+    <script type="text/javascript"
src="../../ui/jquery.ui.autocomplete.js"></script>
+    <link type="text/css" href="../demos.css" rel="stylesheet" />
+    <script type="text/javascript">
+    $(function() {
+        function log(message) {
+            $("<div/>").text(message).prependTo("#log");
+            $("#log").attr("scrollTop", 0);
+        }
+
+        $("#city").autocomplete({
+            source: function(request, response) {
+                $.ajax({
+                    url: "http://ws.geonames.org/searchJSON",
+                    dataType: "jsonp",
+                    data: {
+                        featureClass: "P",
+                        style: "full",
+                        maxRows: 15,
+                        name_startsWith: request.term
+                    },
+                    success: function(data) {
+                        response($.map(data.geonames, function(item) {
+                            return {
+                                label: item.name + (item.adminName1 ? ", " + item.adminName1 : "")
+ ", " + item.countryName,
+                                result: item.name
+                            }
+                        }))
+                    }
+                })
+            },
+            minLength: 2,
+            change: function(event, ui) {
+                log(ui.item ? ("Selected: " + ui.item.label) : "Nothing selected,
input was " + this.value);
+            },
+            open: function() {
+                $(this).removeClass("ui-corner-all").addClass("ui-corner-top");
+            },
+            close: function() {
+                $(this).removeClass("ui-corner-top").addClass("ui-corner-all");
+            }
+        });
+    });
+    </script>
+    <style>
+        .ui-autocomplete-loading { background: url(indicator.gif) no-repeat
right; }
+        #city { width: 25em; }
+    </style>
+</head>
+<body>
+
+<div class="demo">
+
+<div class="ui-widget">
+    <label for="city">Your city: </label>
+    <input class="ui-widget ui-widget-content ui-corner-all" id="city" />
+    Powered by <a href="http://geonames.org">geonames.org</a>
+</div>
+
+<div class="ui-widget" style="margin-top:2em; font-family:Arial">
+    Result:
+    <div id="log" style="height: 200px; width: 300px; overflow: auto;"
class="ui-widget-content"></div>
+</div>
+
+</div><!-- End demo -->
+
+<div class="demo-description">
+


+The Autocomplete widgets provides suggestions while you type into the
field. Here the suggestions are cities, displayed when at least two
characters are entered into the field.
+




+


+In this case, the datasource is the <a
href="http://geonames.org">geonames.org webservice</a>. While only the city
name itself ends up in the input after selecting an element, more info is
displayed in the suggestions to help find the right entry. That data is
also available in callbacks, as illustrated by the Result area below the
input.
+







+</div><!-- End demo-description -->
+
+</body>
+</html>
=======================================
--- /dev/null
+++ /branches/dev/demos/autocomplete/remote-with-cache.html    Tue Dec 15
13:13:03 2009
@@ -0,0 +1,75 @@
+<!doctype html>
+<html>
+<head>
+    <title>jQuery UI Autocomplete Remote with caching demo</title>
+    <link type="text/css" href="../../themes/base/ui.all.css"
rel="stylesheet" />
+    <script type="text/javascript" src="../../jquery-1.3.2.js"></script>
+    <script type="text/javascript" src="../../ui/jquery.ui.core.js"></script>
+    <script type="text/javascript"
src="../../ui/jquery.ui.position.js"></script>
+    <script type="text/javascript"
src="../../ui/jquery.ui.autocomplete.js"></script>
+    <link type="text/css" href="../demos.css" rel="stylesheet" />
+    <script type="text/javascript">
+    $(function() {
+        function log(message) {
+            $("<div/>").text(message).prependTo("#log");
+            $("#log").attr("scrollTop", 0);
+        }
+
+        var cache = {};
+        $("#birds").autocomplete({
+            source: function(request, response) {
+                if (cache.term == request.term && cache.content) {
+                    return cache.content;
+                }
+                if (new RegExp(cache.term).test(request.term) && cache.content &&
cache.content.length < 13) {
+                    var matcher = new
RegExp($.ui.autocomplete.escapeRegex(request.term), "i");
+                    return $.grep(cache.content, function(value) {
+                     return matcher.test(value.result)
+                    });
+                }
+                $.ajax({
+                    url: "search.php",
+                    dataType: "json",
+                    data: request,
+                    success: function(data) {
+                        cache.term = request.term;
+                        cache.content = data;
+                        response(data);
+                    }
+                });
+            },
+            minLength: 2,
+            change: function(event, ui) {
+                log(ui.item ? ("Selected: " + ui.item.result + " aka " +
ui.item.id) : "Nothing selected, input was " + this.value);
+            }
+        });
+    });
+    </script>
+</head>
+<body>
+
+<div class="demo">
+
+<div class="ui-widget">
+    <label for="birds">Birds: </label>
+    <input class="ui-widget ui-widget-content ui-corner-all" id="birds" />
+</div>
+
+<div class="ui-widget" style="margin-top:2em; font-family:Arial">
+    Result:
+    <div id="log" style="height: 200px; width: 300px; overflow: auto;"
class="ui-widget-content"></div>
+</div>
+
+</div><!-- End demo -->
+
+<div class="demo-description">
+


+The Autocomplete widgets provides suggestions while you type into the
field. Here the suggestions are bird names, displayed when at least two
characters are entered into the field.
+




+


+Similar to the remote datasource demo, though this adds some local caching
to improve performance. The cache here saves just one query, and could be
extended to cache multiple results, one for each term.
+




+</div><!-- End demo-description -->
+
+</body>
+</html>
=======================================
--- /dev/null
+++ /branches/dev/demos/autocomplete/remote.html    Tue Dec 15 13:13:03 2009
@@ -0,0 +1,55 @@
+<!doctype html>
+<html>
+<head>
+    <title>jQuery UI Autocomplete Remote datasource demo</title>
+    <link type="text/css" href="../../themes/base/ui.all.css"
rel="stylesheet" />
+    <script type="text/javascript" src="../../jquery-1.3.2.js"></script>
+    <script type="text/javascript" src="../../ui/jquery.ui.core.js"></script>
+    <script type="text/javascript"
src="../../ui/jquery.ui.position.js"></script>
+    <script type="text/javascript"
src="../../ui/jquery.ui.autocomplete.js"></script>
+    <link type="text/css" href="../demos.css" rel="stylesheet" />
+    <script type="text/javascript">
+    $(function() {
+        function log(message) {
+            $("<div/>").text(message).prependTo("#log");
+            $("#log").attr("scrollTop", 0);
+        }
+
+        $("#birds").autocomplete({
+            // TODO doesn't work when loaded from /demos/#autocomplete|remote
+            source: "search.php",
+            minLength: 2,
+            change: function(event, ui) {
+                log(ui.item ? ("Selected: " + ui.item.result + " aka " +
ui.item.id) : "Nothing selected, input was " + this.value);
+            }
+        });
+    });
+    </script>
+</head>
+<body>
+
+<div class="demo">
+
+<div class="ui-widget">
+    <label for="birds">Birds: </label>
+    <input class="ui-widget ui-widget-content ui-corner-all" id="birds" />
+</div>
+
+<div class="ui-widget" style="margin-top:2em; font-family:Arial">
+    Result:
+    <div id="log" style="height: 200px; width: 300px; overflow: auto;"
class="ui-widget-content"></div>
+</div>
+
+</div><!-- End demo -->
+
+<div class="demo-description">
+


+The Autocomplete widgets provides suggestions while you type into the
field. Here the suggestions are bird names, displayed when at least two
characters are entered into the field.
+




+


+The datasource is a server-side script which returns JSON data, specified
via a simple URL for the source-option. In addition, the minLength-option
is set to 2 to avoid queries that would return too many results and the
change-event is used to display some feedback.
+





+</div><!-- End demo-description -->
+
+</body>
+</html>
=======================================
--- /dev/null
+++ /branches/dev/demos/autocomplete/search.php    Tue Dec 15 13:13:03 2009
@@ -0,0 +1,640 @@
+<?php
+
+$q = strtolower($_GET["term"]);
+if (!$q) return;
+$items = array(
+"Great <em>Bittern</em>"=>"Botaurus stellaris",
+"Little <em>Grebe</em>"=>"Tachybaptus ruficollis",
+"Black-necked Grebe"=>"Podiceps nigricollis",
+"Little Bittern"=>"Ixobrychus minutus",
+"Black-crowned Night Heron"=>"Nycticorax nycticorax",
+"Purple Heron"=>"Ardea purpurea",
+"White Stork"=>"Ciconia ciconia",
+"Spoonbill"=>"Platalea leucorodia",
+"Red-crested Pochard"=>"Netta rufina",
+"Common Eider"=>"Somateria