web-dev-qa-db-fra.com

jQuery Mobile: amélioration du balisage du contenu ajouté dynamiquement

Je me demandais comment améliorer dynamiquement la page jQuery Mobile?

J'ai essayé d'utiliser ces méthodes:

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

    et

  2. $('[data-role="page"]').page();

Comment puis-je également empêcher le balisage d'amélioration des cases à cocher uniquement?

72
user2001897

Avertissement:

Cet article peut également être trouvé dans le cadre de mon blog ICI .

Intro:

Il existe plusieurs façons d'améliorer le balisage de contenu créé dynamiquement. Il ne suffit tout simplement pas d'ajouter dynamiquement du nouveau contenu à la page jQuery Mobile , le nouveau contenu doit être amélioré avec jQuery classique Style mobile . Comme il s'agit plutôt de traiter une tâche lourde, il doit y avoir des priorités, si possible jQuery Mobile doit faire le moins d'amélioration possible. N'améliorez pas la page entière si un seul composant doit être stylisé.

Qu'est-ce que tout cela signifie? Lorsque le plugin de page envoie un événement pageInit , que la plupart des widgets utilisent pour s'initialiser automatiquement. il améliorera automatiquement toutes les instances des widgets qu'il trouve sur la page.

Cependant, si vous générez un nouveau balisage côté client ou chargez du contenu via Ajax et l'injectez dans une page, vous pouvez déclencher l'événement create pour gérer l'initialisation automatique de tous les plug-ins contenus dans le nouveau balisage. Cela peut être déclenché sur n'importe quel élément (même la page div elle-même), vous épargnant la tâche d'initialiser manuellement chaque plugin (bouton listview, select, etc.).

Dans cet esprit, discutons des niveaux d'amélioration. Il y en a trois et ils sont classés des moins exigeants en ressources aux plus élevés:

  1. Améliorez un composant/widget unique
  2. Améliorez le contenu d'une page
  3. Améliorez le contenu d'une page complète (en-tête, contenu, pied de page)

Améliorez un composant/widget unique:

Important: Les méthodes d'amélioration ci-dessous doivent être utilisées uniquement sur la page actuelle/active. Pour les pages insérées dynamiquement, ces pages et leur contenu seront améliorés une fois insérés dans DOM. L'appel de n'importe quelle méthode sur des pages créées dynamiquement/autre que la page active entraînera une erreur.

Chaque widget jQuery Mobile peut être amélioré dynamiquement:

  1. Listview :

    Amélioration du balisage:

    $('#mylist').listview('refresh');
    

    Suppression des éléments listview:

    $('#mylist li').eq(0).addClass('ui-screen-hidden'); 
    

    Exemple d'amélioration: http://jsfiddle.net/Gajotres/LrAyE/

    Notez que la méthode refresh () n'affecte que les nouveaux nœuds ajoutés à une liste. Ceci est fait pour des raisons de performances.

    L'un des points forts de la vue de liste est une fonctionnalité de filtrage. Malheureusement, pour une raison quelconque, jQuery Mobile ne parviendra pas à ajouter dynamiquement l'option de filtre à une liste existante. Heureusement, il existe une solution de contournement. Si possible, supprimez la liste actuelle et ajoutez-en une autre avec l'option Filer activée.

    Voici un exemple de travail: https://stackoverflow.com/a/15163984/18486

    $(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');
    });
    
  2. Bouton

    Amélioration du balisage:

    $('[type="button"]').button();
    

    Exemple d'amélioration: http://jsfiddle.net/Gajotres/m4rjZ/

    Encore une chose, vous n'avez pas besoin d'utiliser un élément d'entrée pour créer un bouton, cela peut même être fait avec un div de base, voici un exemple: http://jsfiddle.net/Gajotres/L9xcN/

  3. Navbar

    Amélioration du balisage:

    $('[data-role="navbar"]').navbar();
    

    Exemple d'amélioration: http://jsfiddle.net/Gajotres/w4m2B/

    Voici une démo pour ajouter un onglet de barre de navigation dynamique: http://jsfiddle.net/Gajotres/V6nHp/

    Et un autre dans pagebeforecreate événement: http://jsfiddle.net/Gajotres/SJG8W/

  4. Entrées de texte, entrées de recherche et zones de texte

    Amélioration du balisage:

    $('[type="text"]').textinput();   
    

    Exemple d'amélioration: http://jsfiddle.net/Gajotres/9UQ9k/

  5. Curseurs et interrupteur à bascule

    Amélioration du balisage:

    $('[type="range"]').slider();  
    

    Exemple d'amélioration: http://jsfiddle.net/Gajotres/caCsf/

    Exemple d'amélioration lors de l'événement pagebeforecreate: http://jsfiddle.net/Gajotres/NwMLP/

    Les curseurs sont un peu bogués pour créer dynamiquement, en savoir plus à ce sujet ici: https://stackoverflow.com/a/15708562/18486

  6. Case à cocher et radiobox

    Amélioration du balisage:

    $('[type="radio"]').checkboxradio();
    

    ou si vous souhaitez sélectionner/désélectionner un autre élément Radiobox/Checkbox:

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

    ou

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

    Exemple d'amélioration: http://jsfiddle.net/Gajotres/VAG6F/

  7. Sélectionnez le menu

    Amélioration du balisage:

    $('select').selectmenu();  
    

    Exemple d'amélioration: http://jsfiddle.net/Gajotres/dEXac/

  8. Pliable

    Malheureusement, l'élément pliable ne peut pas être amélioré par une méthode spécifique, donc trigger ('create') doit être utilisé à la place.

    Exemple d'amélioration: http://jsfiddle.net/Gajotres/ck6uK/

  9. Tableau

    Amélioration du balisage:

    $(".selector").table("refresh");
    

    Bien qu'il s'agisse d'un moyen standard d'amélioration des tables, à ce stade, je ne peux pas le faire fonctionner. Donc, utilisez plutôt trigger ('create').

    Exemple d'amélioration: http://jsfiddle.net/Gajotres/Zqy4n/

  10. Panneaux - Nouveau

    Amélioration du balisage du panneau:

    $('.selector').trigger('pagecreate');
    

    Amélioration du balisage de contenu ajouté dynamiquement au Panel:

    $('.selector').trigger('pagecreate');
    

    Exemple: http://jsfiddle.net/Palestinian/PRC8W/

Améliorez le contenu d'une page:

Dans le cas où nous générons/reconstruisons le contenu d'une page entière, il est préférable de tout faire en même temps et cela peut être fait avec ceci:

$('#index').trigger('create');

Exemple d'amélioration: http://jsfiddle.net/Gajotres/426NU/

Améliorez le contenu d'une page complète (en-tête, contenu, pied de page):

Malheureusement pour nous, le déclencheur ("créer") ne peut pas améliorer le balisage d'en-tête et de pied de page. Dans ce cas, nous avons besoin de gros canons:

$('#index').trigger('pagecreate');

Exemple d'amélioration: http://jsfiddle.net/Gajotres/DGZcr/

C'est presque une méthode mystique car je ne la trouve pas dans la documentation officielle jQuery Mobile . Pourtant, il est facilement trouvé dans jQuery Mobile tracker de bogue avec un avertissement de ne pas l'utiliser sauf si c'est vraiment vraiment nécessaire.

Remarque, . Trigger ('pagecreate'); peut supposer être utilisé une seule fois par rafraîchissement de page, je l'ai trouvé faux:

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

Plugins d'amélioration tiers

Il existe plusieurs plugins d'amélioration tiers. Certains sont mis à jour en tant que mise à jour d'une méthode existante et d'autres sont faits pour corriger des fonctionnalités jQM cassées.

  • Modification du texte du bouton

    Malheureusement, je n'ai pas trouvé le développeur de ce plugin. Original SO source: Changer le texte du bouton 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);
    

    Exemple de travail: http://jsfiddle.net/Gajotres/mwB22/

Obtenez la hauteur de contenu maximale correcte

Dans le cas où l'en-tête et le pied de page ont une hauteur de contenu constante, la div peut être facilement définie pour couvrir tout l'espace disponible avec une petite astuce CSS:

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

Et voici un exemple de travail avec Google maps api3 démo: http://jsfiddle.net/Gajotres/7kGdE/

Cette méthode peut être utilisée pour obtenir une hauteur de contenu maximale correcte, et elle doit être utilisée avec un événement 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;
}

Et voici un exemple live jsFiddle: http://jsfiddle.net/Gajotres/nVs9J/

Il y a une chose à retenir. Cette fonction vous permettra d'obtenir correctement la hauteur de contenu maximale disponible et en même temps, elle peut être utilisée pour étirer ce même contenu. Malheureusement, il ne peut pas être utilisé pour étirer img à la hauteur du contenu, la balise img a une surcharge de 3px.

Méthodes de prévention de l'amélioration du balisage:

Cela peut être fait de plusieurs manières, parfois vous devrez les combiner pour obtenir le résultat souhaité.

  • Méthode 1:

    Il peut le faire en ajoutant cet attribut:

    data-enhance="false"
    

    à l'en-tête, contenu, pied de page conteneur.

    Cela doit également être activé lors de la phase de chargement de l'application:

    $(document).one("mobileinit", function () {
        $.mobile.ignoreContentEnabled=true;
    });
    

    Initialisez-le avant l'initialisation de jquery-mobile.js (regardez l'exemple ci-dessous).

    Pour en savoir plus, cliquez ici:

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

    Exemple: http://jsfiddle.net/Gajotres/UZwpj/

    Pour recréer une page à nouveau, utilisez ceci:

    $('#index').live('pagebeforeshow', function (event) {
        $.mobile.ignoreContentEnabled = false;
        $(this).attr('data-enhance','true');
        $(this).trigger("pagecreate")
    });
    
  • Méthode 2:

    La deuxième option est de le faire manuellement avec cette ligne:

    data-role="none"
    

    Exemple: http://jsfiddle.net/Gajotres/LqDke/

  • Méthode 3:

    Certains éléments HTML peuvent être empêchés d'améliorer le balisage:

     $(document).bind('mobileinit',function(){
          $.mobile.page.prototype.options.keepNative = "select, input";
     });    
    

    Exemple: http://jsfiddle.net/Gajotres/gAGtS/

    Encore une fois l'initialiser avant l'initialisation de jquery-mobile.js (regardez l'exemple ci-dessous).

Problèmes d'amélioration du balisage:

Parfois, lors de la création d'un composant à partir de zéro (comme listview), cette erreur se produit:

impossible d'appeler des méthodes sur listview avant l'initialisation

Il peut être évité avec l'initialisation du composant avant l'amélioration du balisage, voici comment résoudre ce problème:

$('#mylist').listview().listview('refresh');

Problèmes de surcharge de balisage:

Si, pour une raison quelconque, jQuery Mobile CSS par défaut doit être modifié, cela doit être fait avec !important remplacer. Sans cela, les styles CSS par défaut ne peuvent pas être modifiés.

Exemple:

#navbar li {
    background: red !important;
}

jsFiddle exemple: http://jsfiddle.net/Gajotres/vTBGa/

Changements:

  • 01.02.2013 - Ajout d'une démonstration dynamique de la barre de navigation
  • 01.03.2013 - Ajout d'un commentaire sur la façon d'ajouter dynamiquement le filtrage à une vue de liste
  • 07.03.2013 - Ajout d'un nouveau chapitre: Obtenez la hauteur de contenu maximale correcte
  • 17.03.2013 - Ajout de quelques mots au chapitre: Obtenez la hauteur de contenu maximale correcte
  • 29.03.2013 - Ajout d'un nouveau contenu sur les curseurs créés dynamiquement et correction d'un exemple de bug
  • 03.04.2013 - Ajout d'un nouveau contenu sur les éléments pliables créés dynamiquement
  • 04.04.2013 - Ajout d'un chapitre sur les plugins tiers
  • 20.05.2013 - Ajout de panneaux et contenus ajoutés dynamiquement
  • 21.05.2013 - Ajout d'une autre façon de définir la hauteur totale du contenu
  • 20.06.2013 - Ajout d'un nouveau chapitre: Problèmes de surcharge de balisage
  • 29.06.2013 - Ajout d'une note importante sur QUAND utiliser les méthodes d'amélioration
165
Gajotres

Depuis JQMobile 1.4, vous pouvez faire .enhanceWithin () sur tous les enfants http://api.jquerymobile.com/enhanceWithin/

var content = '<p>Hi</p>';
$('#somediv').html(content);
$('#somediv').enhanceWithin();
4
zzart