JQuery mobile 中的多个可过滤选择菜单

Posted

技术标签:

【中文标题】JQuery mobile 中的多个可过滤选择菜单【英文标题】:Multiple filterable select menus in JQuery mobile 【发布时间】:2014-07-19 02:13:18 【问题描述】:

我正在使用 JQuery Mobile 版本 1.4.2,并且在我的一个模板中的某个时刻,我想使用 irs 可过滤选择菜单。但是有一个问题:

那个特定的元素有一个特定的 ID id="filter-menu" 这意味着我只能在每个模板中使用它一次(例如,仅用于苹果列表)。

所以我要问:如何在同一个网页中多次使用它?

提前致谢。

【问题讨论】:

【参考方案1】:

您可以使用任何您想要的 id,只要此 id 连接特定的选择和过滤器输入。

示例:http://jsfiddle.net/8e5q9/

html

<!DOCTYPE html>
<html>
    <head>
        <title>jQM Complex Demo</title>
        <meta http-equiv='Content-Type' content='text/html; charset=utf-8'/>
        <meta name="viewport" content="width=device-width; initial-scale=1.0; maximum-scale=1.0; minimum-scale=1.0; user-scalable=no; target-densityDpi=device-dpi"/>
        <link rel="stylesheet" href="http://code.jquery.com/mobile/1.4.2/jquery.mobile-1.4.2.min.css" /> 
        <!--<script src="http://code.jquery.com/jquery-1.10.1.min.js"></script>-->
        <script src="http://code.jquery.com/mobile/1.4.2/jquery.mobile-1.4.2.min.js"></script>    
    </head>
    <body>     
        <div data-role="page" id="index" data-theme="a" >
            <div data-role="header">
                <h3>
                    First Page
                </h3>
                <a href="#second" class="ui-btn-right">Next</a>
            </div>

            <div data-role="content">
                <form>
                    <input type="text" data-type="search" id="filterable-input1"/>
                </form>
                <form data-role="controlgroup" data-filter="true" data-input="#filterable-input1">
                    <label for="pizza">
                        Pizza
                        <input type="checkbox" id="pizza"/>
                    </label>
                    <label for="goulash">
                        Goulash
                        <input type="checkbox" id="goulash"/>
                    </label>
                    <label for="falafel">
                        Falafel
                        <input type="checkbox" id="falafel"/>
                    </label>
                    <label for="spring-rolls">
                        Spring Rolls
                        <input type="checkbox" id="spring-rolls"/>
                    </label>
                </form>
                <form>
                    <input type="text" data-type="search" id="filterable-input2"/>
                </form>
                <form data-role="controlgroup" data-filter="true" data-input="#filterable-input2">
                    <label for="pizza">
                        Pizza
                        <input type="checkbox" id="pizza"/>
                    </label>
                    <label for="goulash">
                        Goulash
                        <input type="checkbox" id="goulash"/>
                    </label>
                    <label for="falafel">
                        Falafel
                        <input type="checkbox" id="falafel"/>
                    </label>
                    <label for="spring-rolls">
                        Spring Rolls
                        <input type="checkbox" id="spring-rolls"/>
                    </label>
                </form>    
            </div>

            <div data-role="footer" data-position="fixed">

            </div>
        </div> 
        <div data-role="page" id="second" data-theme="a" >
            <div data-role="header">
                <h3>
                    Second Page
                </h3>
                <a href="#index" class="ui-btn-left">Back</a>
            </div>

            <div data-role="content">

            </div>

            <div data-role="footer" data-position="fixed">

            </div>
        </div>  
    </body>
</html>    

注意在一种情况下我是如何使用 #filterable-input1 而在另一种情况下是如何使用 #filterable-input2

更新

这又是一个小菜一碟,下次你自己试试吧,我不是要取笑你,这就是你要学会自我传递的方式。

工作示例:http://jsfiddle.net/Gajotres/zCq98/

HTML:

<form>
    <select id="filter-menu" data-native-menu="false">
        <option value="SFO">San Francisco1</option>
        <option value="LAX">Los Angeles1</option>
        <option value="YVR">Vancouver1</option>
        <option value="YYZ">Toronto1</option>
    </select>
</form>
<form>
    <select id="filter-menu2" data-native-menu="false">
        <option value="SFO">San Francisco2</option>
        <option value="LAX">Los Angeles2</option>
        <option value="YVR">Vancouver2</option>
        <option value="YYZ">Toronto2</option>
    </select>
</form>

javascript

    $.mobile.document
    // "filter-menu-menu" is the ID generated for the listview when it is created
    // by the custom selectmenu plugin. Upon creation of the listview widget we
    // want to prepend an input field to the list to be used for a filter.
    .on( "listviewcreate", "#filter-menu-menu, #filter-menu2-menu", function( e ) 
        var input,
            listbox = $( "#filter-menu-listbox" ),
            form = listbox.jqmData( "filter-form" ),
            listview = $( e.target );
        // We store the generated form in a variable attached to the popup so we
        // avoid creating a second form/input field when the listview is
        // destroyed/rebuilt during a refresh.
        if ( !form ) 
            input = $( "<input data-type='search'></input>" );
            form = $( "<form></form>" ).append( input );
            input.textinput();
            $( "#filter-menu-listbox" )
            .prepend( form )
            .jqmData( "filter-form", form );
        
        // Instantiate a filterable widget on the newly created listview and
        // indicate that the generated input is to be used for the filtering.
        listview.filterable( input: input );
    )
    // The custom select list may show up as either a popup or a dialog,
    // depending how much vertical room there is on the screen. If it shows up
    // as a dialog, then the form containing the filter input field must be
    // transferred to the dialog so that the user can continue to use it for
    // filtering list items.
    //
    // After the dialog is closed, the form containing the filter input is
    // transferred back into the popup.
    .on( "pagebeforeshow pagehide", "#filter-menu-dialog", function( e ) 
        var form = $( "#filter-menu-listbox" ).jqmData( "filter-form" ),
            placeInDialog = ( e.type === "pagebeforeshow" ),
            destination = placeInDialog ? $( e.target ).find( ".ui-content" ) : $( "#filter-menu-listbox" );
        form
        .find( "input" )
        // Turn off the "inset" option when the filter input is inside a dialog
        // and turn it back on when it is placed back inside the popup, because
        // it looks better that way.
        .textinput( "option", "inset", !placeInDialog )
        .end()
        .prependTo( destination );
    );

如何:

这并不难。我只更改了这一行:

.on( "listviewcreate", "#filter-menu-menu, #filter-menu2-menu", function( e ) 

此更改的原因是选择框名称:#filter-menu 和 #filter-menu2

#filter-menu  --> #filter-menu-menu
#filter-menu2 --> #filter-menu2-menu

【讨论】:

感谢您的麻烦,但我正在寻找类似的内容:demos.jquerymobile.com/1.4.2/selectmenu-custom-filter ..x3 用于我的三个列表中的每一个。【参考方案2】:

我从你提到的 jquery 移动网站 (http://demos.jquerymobile.com/1.4.2/selectmenu-custom-filter/) 获得了这段代码,你只需要在 html 部分提供 id,其他事情将由 jquery mobile 完成,我已经在 3 个长列表及其像魅力一样工作,但问题是我无法将它与通过 js 动态生成的列表一起使用,我将在获得动态列表的解决方案后立即更新我的答案。

(function ($) 
    function pageIsSelectmenuDialog(page) 
        var isDialog = false,
            id = page && page.attr("id");
        $(".filterable-select").each(function () 
            if ($(this).attr("id") + "-dialog" === id) 
                isDialog = true;
                return false;
            
        );
        return isDialog;
    
    $.mobile.document
        // Upon creation of the select menu, we want to make use of the fact that the ID of the
        // listview it generates starts with the ID of the select menu itself, plus the suffix "-menu".
        // We retrieve the listview and insert a search input before it.
        .on("selectmenucreate", ".filterable-select", function (event) 
            var input,
                selectmenu = $(event.target),
                list = $("#" + selectmenu.attr("id") + "-menu"),
                form = list.jqmData("filter-form");
            // We store the generated form in a variable attached to the popup so we avoid creating a
            // second form/input field when the listview is destroyed/rebuilt during a refresh.
            if (!form) 
                input = $("<input data-type='search'></input>");
                form = $("<form></form>").append(input);
                input.textinput();
                list
                    .before(form)
                    .jqmData("filter-form", form);
                form.jqmData("listview", list);
            
            // Instantiate a filterable widget on the newly created selectmenu widget and indicate that
            // the generated input form element is to be used for the filtering.
            selectmenu
                .filterable(
                    input: input,
                    children: "> option[value]"
                )
                // Rebuild the custom select menu's list items to reflect the results of the filtering
                // done on the select menu.
                .on("filterablefilter", function () 
                    selectmenu.selectmenu("refresh");
                );
        )
        // The custom select list may show up as either a popup or a dialog, depending on how much
        // vertical room there is on the screen. If it shows up as a dialog, then the form containing
        // the filter input field must be transferred to the dialog so that the user can continue to
        // use it for filtering list items.
        .on("pagecontainerbeforeshow", function (event, data) 
            var listview, form;
            // We only handle the appearance of a dialog generated by a filterable selectmenu
            if (!pageIsSelectmenuDialog(data.toPage)) 
                return;
            
            listview = data.toPage.find("ul");
            form = listview.jqmData("filter-form");
            // Attach a reference to the listview as a data item to the dialog, because during the
            // pagecontainerhide handler below the selectmenu widget will already have returned the
            // listview to the popup, so we won't be able to find it inside the dialog with a selector.
            data.toPage.jqmData("listview", listview);
            // Place the form before the listview in the dialog.
            listview.before(form);
        )
        // After the dialog is closed, the form containing the filter input is returned to the popup.
        .on("pagecontainerhide", function (event, data) 
            var listview, form;
            // We only handle the disappearance of a dialog generated by a filterable selectmenu
            if (!pageIsSelectmenuDialog(data.prevPage)) 
                return;
            
            listview = data.prevPage.jqmData("listview"),
            form = listview.jqmData("filter-form");
            // Put the form back in the popup. It goes ahead of the listview.
            listview.before(form);
        );
)(jQuery);
<form>
    <div class="ui-field-contain" data-role="none" data-native-menu="false">
                                    
         <select name="Language" id="Language" data-native-menu="false"                                            class="filterable-select" data-force-dialog="true" data-filter="true" data-mini="true">
            <option value="1">- Select1 - </option>
            <option value="1">- Select1 - </option>
            <option value="1">- Select1 - </option>
            <option value="1">- Select1 - </option>
            <option value="1">- Select1 - </option>
            <option value="1">- Select1 - </option>
         </select>
    </div>
</form>

编辑:- 对于动态数据,我刚刚添加了 $('#IdOfSelectMenu').selectmenu().selectmenu('refresh');

【讨论】:

以上是关于JQuery mobile 中的多个可过滤选择菜单的主要内容,如果未能解决你的问题,请参考以下文章

jQuery mobile - 动态切换选择菜单到多个

如何修改jQuery mobile子菜单中的关闭按钮以进行初始打开

jQuery Mobile 自定义选择菜单适用于 Mobile Safari,但不适用于 UIWebView

jQuery Mobile 表单选择菜单

jQuery Mobile 表单选择菜单

如何修复 jQuery mobile 子菜单中的标题