javascript - jQuery 移动 : Markup Enhancement of dynamically added content

标签 javascript jquery html cordova jquery-mobile

我想知道如何动态增强 jQuery Mobile 页面?
我曾尝试使用这些方法:

  • $('[data-role="page"]').trigger('create');
  • $('[data-role="page"]').page();

  • 另外,如何仅防止复选框的增强标记?

    最佳答案

    免责声明:

    这篇文章也可以在我的博客 HERE 中找到。

    介绍:

    有多种方法可以增强动态创建的内容标记。仅将新内容动态添加到 jQuery Mobile 页面是不够的,必须使用经典的 jQuery Mobile 样式增强新内容因为这是处理繁重的任务,所以需要一些优先级,如果可能的话 jQuery Mobile 需要做尽可能少的增强。如果只需要设置一个组件的样式,则不要增强整个页面。

    这一切意味着什么?当页面插件调度 pageInit 事件时,大多数小部件使用它来自动初始化自己。它将自动增强它在页面上找到的小部件的任何实例。

    但是,如果您在客户端生成新标记或通过 Ajax 加载内容并将其注入(inject)页面,则可以触发 create 事件来处理新标记中包含的所有插件的自动初始化。这可以在任何元素(甚至页面 div 本身)上触发,从而为您省去手动初始化每个插件( ListView 按钮、选择等)的任务。

    考虑到这一点,让我们讨论增强级别。其中有三个,它们从资源需求较低的到较高的排序:

  • 增强单个组件/小部件
  • 增强页面内容
  • 增强整页内容(页眉、内容、页脚)

  • 增强单个组件/小部件:

    Important: The below enhancement methods are to be used only on current/active page. For dynamically inserted pages, those pages and their contents will be enhanced once inserted into DOM. Calling any method on dynamically created pages / other than the active page, will result an error.



    每个 jQuery Mobile 小部件都可以动态增强:
  • Listview :

    标记增强:
    $('#mylist').listview('refresh');
    

    删除 ListView 元素:
    $('#mylist li').eq(0).addClass('ui-screen-hidden'); 
    

    增强示例:http://jsfiddle.net/Gajotres/LrAyE/

    请注意,refresh() 方法仅影响附加到列表的新节点。这样做是出于性能原因。

    ListView 的亮点之一是过滤功能。不幸的是,由于某种原因,jQuery Mobile 将无法向现有 ListView 动态添加过滤器选项。幸运的是,有一个解决方法。如果可能,删除当前 ListView 并添加另一个打开文件管理器选项的 ListView 。

    这是一个工作示例:https://stackoverflow.com/a/15163984/1848600
    $(document).on('pagebeforeshow', '#index', function(){       
        $('<ul>').attr({'id':'test-listview','data-role':'listview', 'data-filter':'true','data-filter-placeholder':'Search...'}).appendTo('#index [data-role="content"]');
        $('<li>').append('<a href="#">Audi</a>').appendTo('#test-listview');
        $('<li>').append('<a href="#">Mercedes</a>').appendTo('#test-listview');
        $('<li>').append('<a href="#">Opel</a>').appendTo('#test-listview');
        $('#test-listview').listview().listview('refresh');
    });
    
  • Button

    标记增强:
    $('[type="button"]').button();
    

    增强示例:http://jsfiddle.net/Gajotres/m4rjZ/

    还有一件事,你不需要使用 input 元素来创建一个按钮,它甚至可以用一个基本的 div 来完成,这是一个例子:http://jsfiddle.net/Gajotres/L9xcN/
  • Navbar

    标记增强:
    $('[data-role="navbar"]').navbar();
    

    增强示例:http://jsfiddle.net/Gajotres/w4m2B/

    这是一个如何添加动态导航栏选项卡的演示:http://jsfiddle.net/Gajotres/V6nHp/

    还有一个在 pagebeforecreate 事件:http://jsfiddle.net/Gajotres/SJG8W/
  • Text inputs, Search inputs & Textareas

    标记增强:
    $('[type="text"]').textinput();   
    

    增强示例:http://jsfiddle.net/Gajotres/9UQ9k/
  • Sliders & Flip toggle switch

    标记增强:
    $('[type="range"]').slider();  
    

    增强示例:http://jsfiddle.net/Gajotres/caCsf/

    pagebeforecreate 事件期间的增强示例:http://jsfiddle.net/Gajotres/NwMLP/

    动态创建滑块有点麻烦,请在此处阅读更多相关信息:https://stackoverflow.com/a/15708562/1848600
  • Checkbox & Radiobox

    标记增强:
    $('[type="radio"]').checkboxradio();
    

    或者如果您想选择/取消选择另一个 Radiobox/Checkbox 元素:
    $("input[type='radio']").eq(0).attr("checked",false).checkboxradio("refresh");
    

    要么
    $("input[type='radio']").eq(0).attr("checked",true).checkboxradio("refresh");
    

    增强示例:http://jsfiddle.net/Gajotres/VAG6F/
  • Select menu

    标记增强:
    $('select').selectmenu();  
    

    增强示例:http://jsfiddle.net/Gajotres/dEXac/
  • Collapsible

    不幸的是,无法通过某些特定方法增强可折叠元素,因此必须使用 trigger('create') 代替。

    增强示例:http://jsfiddle.net/Gajotres/ck6uK/
  • Table

    标记增强:
    $(".selector").table("refresh");
    

    虽然这是表增强的标准方式,但此时我无法使其工作。所以改用触发器('创建')。

    增强示例:http://jsfiddle.net/Gajotres/Zqy4n/
  • Panels - 新

    面板标记增强:
    $('.selector').trigger('pagecreate');
    

    动态添加到 Panel 的内容的标记增强:
    $('.selector').trigger('pagecreate');
    

    示例:http://jsfiddle.net/Palestinian/PRC8W/

  • 增强页面内容:

    如果我们正在生成/重建整个页面内容,最好一次完成,并且可以通过以下方式完成:
    $('#index').trigger('create');
    

    增强示例:http://jsfiddle.net/Gajotres/426NU/

    增强整页内容(页眉、内容、页脚):

    不幸的是,trigger('create') 不能增强页眉和页脚标记。在这种情况下,我们需要大枪:
    $('#index').trigger('pagecreate');
    

    增强示例:http://jsfiddle.net/Gajotres/DGZcr/

    这几乎是一个神秘的方法,因为我在官方 jQuery Mobile 文档中找不到它。仍然很容易在 jQuery Mobile 错误跟踪器中找到它,并警告不要使用它,除非确实有必要。

    注意, .trigger('pagecreate'); 可以假设每次页面刷新只能使用一次,我发现它是不真实的:

    http://jsfiddle.net/Gajotres/5rzxJ/

    第 3 方增强插件

    有几个 3rd 方增强插件。有些是作为对现有方法的更新,有些是为了修复损坏的 jQM 功能。
  • 按钮文字更改

    不幸的是找不到这个插件的开发者。原始 SO 来源:Change button text jquery mobile
    (function($) {
        /*
         * Changes the displayed text for a jquery mobile button.
         * Encapsulates the idiosyncracies of how jquery re-arranges the DOM
         * to display a button for either an <a> link or <input type="button">
         */
        $.fn.changeButtonText = function(newText) {
            return this.each(function() {
                $this = $(this);
                if( $this.is('a') ) {
                    $('span.ui-btn-text',$this).text(newText);
                    return;
                }
                if( $this.is('input') ) {
                    $this.val(newText);
                    // go up the tree
                    var ctx = $this.closest('.ui-btn');
                    $('span.ui-btn-text',ctx).text(newText);
                    return;
                }
            });
        };
    })(jQuery);
    

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

  • 获取正确的最大内容高度

    如果页面页眉和页脚具有恒定高度的内容 div 可以很容易地设置为使用一个小 css 技巧来覆盖全部可用空间:

    #content {
        padding: 0;
        position : absolute !important; 
        top : 40px !important;  
        right : 0; 
        bottom : 40px !important;  
        left : 0 !important;     
    }
    

    这是一个工作示例,其中 Google maps api3 演示:http://jsfiddle.net/Gajotres/7kGdE/

    此方法可用于获取正确的最大内容高度,并且必须与 pageshow 事件一起使用。
    function getRealContentHeight() {
        var header = $.mobile.activePage.find("div[data-role='header']:visible");
        var footer = $.mobile.activePage.find("div[data-role='footer']:visible");
        var content = $.mobile.activePage.find("div[data-role='content']:visible:visible");
        var viewport_height = $(window).height();
    
        var content_height = viewport_height - header.outerHeight() - footer.outerHeight();
        if((content.outerHeight() - header.outerHeight() - footer.outerHeight()) <= viewport_height) {
            content_height -= (content.outerHeight() - content.height());
        } 
        return content_height;
    }
    

    这是一个实时的 jsFiddle 示例:http://jsfiddle.net/Gajotres/nVs9J/

    有一件事要记住。此功能将正确获得最大可用内容高度,同时它可用于拉伸(stretch)相同的内容。不幸的是,它不能用于将 img 拉伸(stretch)到完整的内容高度,img 标签的开销为 3px。

    标记增强预防方法:

    这可以通过几种方式完成,有时您需要将它们组合起来以达到预期的结果。
  • 方法一:

    它可以通过添加此属性来实现:
    data-enhance="false"
    

    到页眉、内容、页脚容器。

    这也需要在应用加载阶段打开:
    $(document).one("mobileinit", function () {
        $.mobile.ignoreContentEnabled=true;
    });
    

    在jquery-mobile.js 初始化之前进行初始化(看下面的例子)。

    可以在此处找到有关此内容的更多信息:

    http://jquerymobile.com/test/docs/pages/page-scripting.html

    示例:http://jsfiddle.net/Gajotres/UZwpj/

    要再次重新创建页面,请使用以下命令:
    $('#index').live('pagebeforeshow', function (event) {
        $.mobile.ignoreContentEnabled = false;
        $(this).attr('data-enhance','true');
        $(this).trigger("pagecreate")
    });
    
  • 方法二:

    第二种选择是使用此行手动执行:
    data-role="none"
    

    示例:http://jsfiddle.net/Gajotres/LqDke/
  • 方法三:

    可以阻止某些 HTML 元素进行标记增强:
     $(document).bind('mobileinit',function(){
          $.mobile.page.prototype.options.keepNative = "select, input";
     });    
    

    示例:http://jsfiddle.net/Gajotres/gAGtS/

    在 jquery-mobile.js 初始化之前再次初始化它(看下面的例子)。

  • 标记增强问题:

    有时从头开始创建组件(如 listview)时会出现此错误:

    cannot call methods on listview prior to initialization



    在标记增强之前通过组件初始化可以防止它,这是您可以解决此问题的方法:
    $('#mylist').listview().listview('refresh');
    

    标记覆盖问题:

    如果由于某种原因需要更改默认的 jQuery Mobile CSS,则必须使用 !important 覆盖来完成。没有它,默认 css 样式无法更改。

    例子:

    #navbar li {
        background: red !important;
    }
    

    jsFiddle 示例:http://jsfiddle.net/Gajotres/vTBGa/

    变化:
  • 01.02.2013 - 添加了动态导航栏演示
  • 01.03.2013 - 添加了关于如何向 ListView 动态添加过滤的注释
  • 07.03.2013 - 添加了新章节: 获取正确的最大内容高度
  • 17.03.2013 - 在章节中添加了几句话: 获取正确的最大内容高度
  • 29.03.2013 - 添加了有关动态创建的滑块的新内容并修复了示例错误
  • 03.04.2013 - 添加了关于动态创建的可折叠元素的新内容
  • 04.04.2013 - 添加了第 3 方插件章节
  • 20.05.2013 - 添加动态添加的面板和内容
  • 21.05.2013 - 添加了另一种设置完整内容高度的方法
  • 20.06.2013 - 添加了新章节: 标记覆盖问题
  • 29.06.2013 - 添加了重要的注意事项 WHEN 使用增强方法
  • 关于javascript - jQuery 移动 : Markup Enhancement of dynamically added content,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14550396/

    相关文章:

    javascript - 如何在 javascript 中将 "break up"数字分成更小的部分?

    javascript - 使用 Javascript 正则表达式,如何在某些短语之间获取值..?

    html - 我怎样才能阻止我的 div 滚动?

    javascript - 无法从 'selectionStart' 读取 'HTMLInputElement' 属性 :

    javascript - 如何使用 JavaScript 拆分并加粗该字符串?

    javascript - 尝试用 js 调整 2 个框的大小,不会动态工作

    javascript - 设置最大边界不起作用 Leaflet

    jqueryUI自定义按钮不显示

    javascript - this.element 的closest() 无法正常工作

    jquery - 在 jquery 验证器中添加自定义方法