如何使用jquery + ajax进行多个依赖的下拉列表

时间:2012-05-17 22:51:02

标签: javascript jquery ajax

我正在尝试构建一个用户可以互相提供工作表的页面。

我正在尝试依赖下拉列表。不确定这是否适合它,所以我将提供一个例子。

粗略地说,集合分类如下: 类型>分类>主题>片

我的想法大致是:

  1. 页面为类型加载json并显示类型下拉列表
  2. 用户将数学,科学,英语视为类型并选择数学
  3. Page使用ajax查询数据库并使用1级,2级,3级等填充主题
  4. 用户选择4年级
  5. Page使用ajax查询数据库并填充相应的4年级主题
  6. ...依此类推,直至链条的底部
  7. 在javascript部分:

    <script type="text/javascript" language="javascript">
        var types;
        var categories;
        var topics;
        var sheets;
    
        //load the first types
        $(document).ready(function(){
            $.ajax({
                async: false,
                url: "base_url/json_get_all_wstypes",
                type: 'POST',
                dataType: 'json',
                success: function(output_string){
                    types = output_string;
                }
            });
        });
    
        //by default - intialize types
        $(document).ready(function(){
            var t_choices = "<select name=\"type_id\" id=\"type_picker\" >";
            t_choices += "<option value=\"\" selected=\"selected\">Select a Type</option>";
    
            $.each(types, function(){
                t_choices += "<option value=\"" + this.type_id.toString() + "\">";
                t_choices += this.type_name.toString();
                t_choices += "</option>";
            });
    
            t_choices += "</select>";
    
            $('#type_choices').text('');
            $(t_choices).appendTo('#type_choices');
        });
    
        //reaction to picking a type 
        $(document).ready(function(){
            $('#type_picker').change(function(){
                var url_arg = $('#type_picker').val().toString();
                var full_url = "base_url/json_get_wscategories_by_type/" + url_arg;
    
                $.ajax({
                    async: false,
                    url: full_url,
                    type: 'POST',
                    dataType: 'json',
                    success: function(output_string){
                        categories = output_string;
                    }
                });
    
                var choices = "<select name=\"category_id\" id=\"category_picker\" >"; 
                choices += "<option value=\"\" selected=\"selected\">Select a category</option>";
    
                $.each( categories, function() {
                    choices += "<option value=\"" + this.category_id.toString() + "\">";
                    choices += this.category_name.toString();
                    choices += "</option>";
                });
    
                choices += "</select>";
    
                alert(choices.toString());
    
                $('#category_choices').text('');
                $(choices).appendTo('#category_choices');
    
            });
        }); 
    
        //reaction to picking a category (initialize topic)     
        $(document).ready(function(){
            $('#category_picker').change(function(){
                var url_arg = $('#category_picker').val().toString();
                var full_url = "base_url/json_get_wstopics_by_category/" + url_arg;
    
                $.ajax({
                    async: false,
                    url: full_url,
                    type: 'POST',
                    dataType: 'json',
                    success: function(output_string){
                        topics = output_string;
                    }
                });
    
                var choices = "<select name=\"topic_id\" id=\"topic_picker\" >"; 
                choices += "<option value=\"\" selected=\"selected\">Topic a category</option>";
    
                $.each( topics, function() {
                    choices += "<option value=\"" + this.topic_id.toString() + "\">";
                    choices += this.topic_name.toString();
                    choices += "</option>";
                });
    
                choices += "</select>";
    
                alert(choices.toString());
    
                $('#topic_choices').text('');
                $(choices).appendTo('#topic_choices');
    
            });
        }); 
    
        //reaction to picking a topic (initialize sheet)
        similar code pattern as method before it...
    
        //reaction to picking a sheet (intialize page)
        similar code pattern as the method before...
    </script>
    

    在网络表单部分:

    <p>
    <label for="type_id">Pick a sheet type:</label>
    <div id="type_choices">
    </div>
    </p>
    
    
    <p>
    <label for="categories_id">Pick a category:</label>
    <div id="category_choices">
    </div>
    </p>
    
    <p>
    <label for="topic_id">Pick a topic:</label>
    <div id="topic_choices">
    
    </div>
    </p>
    
    <p>
    <label for="worksheet_id">Pick a worksheet:</label>
    <div id="sheet_choices">
    Please select a topic first to activate this section
    </div>
    </p>
    

    这适用于选择类型并加载类别的显示,但一旦我选择类别没有任何反应。此外,如果有人能指出我在网络世界中所谓的内容,我会非常感激。动态依赖下拉不是很有用,我不知道还有什么可以称之为。

1 个答案:

答案 0 :(得分:3)

您的代码不必要地依赖于jQuery,并且不会有效地重用代码。这个解决方案可能需要对服务器端代码进行细微的重写,但无论如何都应该更抽象。尝试更像这样的东西:

<html>
<body>
<select id="type" onchange="updateNext(this, 'category')">
    <option value="a">A</option>
    <option value="b">B</option>
    <option value="c">C</option>
</select>
<select id="category" onchange="updateNext(this, 'topic')">
</select>
<select id="topic" onchange="updateNext(this, 'worksheet')">
</select>
<script>
    function updateNext(el, nextName) {
        var url_arg = el.value;
        var full_url = "base_url/json_get_wstopics_by_category/" + url_arg;
        var options, txtStrng;
        //grab ajax data
        $.ajax({
            async: false,
            url: full_url,
            type: 'POST',
            dataType: 'json',
            success: function(output_string){
                options= output_string;
            }
        });
        //create the option list
        $.each( options, function() {
            txtStrng += "<option value=\"" + this.option_id.toString() + "\">";
            txtStrng += this.option_name.toString();
            txtStrng += "</option>";
        });
        //clear the option list
        $('#'+nextName).text('');
        //attach the option list
        $(txtStrng).appendTo('#'+nextName);
    }
</script>