web-dev-qa-db-fra.com

Comment puis-je rendre une div glissable pour un écran tactile de l'interface utilisateur jQuery 'draggable ()'?

J'ai une interface utilisateur jQuery draggable() qui fonctionne dans Firefox et Chrome. Le concept d'interface utilisateur consiste essentiellement à cliquer pour créer un élément de type "post-it".

En gros, je clique ou tape sur div#everything (100% de hauteur et de largeur) qui écoute les clics et un texte de saisie s'affiche. Vous ajoutez du texte, puis lorsque vous avez terminé, il l'enregistre. Vous pouvez faire glisser cet élément autour. Cela fonctionne sur les navigateurs normaux, mais sur un iPad, je peux tester avec, je ne peux pas faire glisser les éléments. Si je touche pour sélectionner (il s'assombrit alors légèrement), je ne peux pas alors le faire glisser. Cela ne traîne pas à gauche ou à droite du tout. Je peux glisser vers le haut ou le bas, mais je ne fais pas glisser l'individu div, je fais glisser toute la page Web.

Alors voici le code que j'utilise pour capturer les clics:

$('#everything').bind('click', function(e){
    var elem = document.createElement('DIV');
    STATE.top = e.pageY;
    STATE.left = e.pageX;
    var e = $(elem).css({
        top: STATE.top,
        left: STATE.left
    }).html('<textarea></textarea>')
    .addClass('instance')
    .bind('click', function(event){
        return false;
    });
    $(this).append(e);
});

Et voici le code que j'utilise pour "enregistrer" la note et transformer la division d'entrée en une simple division d'affichage:

$('textarea').live('mouseleave', function(){
    var val = jQuery.trim($(this).val());
    STATE.content = val;
    if (val == '') {
        $(this).parent().remove();
    } else {
        var div  = $(this).parent();
        div.text(val).css({
            height: '30px'
        });
        STATE.height = 30;
        if ( div.width() !== div[0].clientWidth || div.height () !== div[0].clientHeight ) {
            while (div.width() !== div[0].clientWidth || div.height () !== div[0].clientHeight) {
                var h = div.height() + 10;
                STATE.height = h;
                div.css({
                    height: (h) + 'px'
                });     // element just got scrollbars
            }
        }
        STATE.guid = uniqueID()
        div.addClass('savedNote').attr('id', STATE.guid).draggable({
            stop: function() {
                var offset = $(this).offset();
                STATE.guid = $(this).attr('id');
                STATE.top = offset.top;
                STATE.left = offset.left;
                STATE.content = $(this).text();
                STATE.height = $(this).height();
                STATE.save();
            }
        });
        STATE.save();
        $(this).remove();
    }
});

Et j'ai ce code quand je charge la page pour les notes sauvegardées:

$('.savedNote').draggable({
    stop: function() {
        STATE.guid = $(this).attr('id');
        var offset = $(this).offset();
        STATE.top = offset.top;
        STATE.left = offset.left;
        STATE.content = $(this).text();
        STATE.height = $(this).height();
        STATE.save();
    }
});

Mon objet STATE gère l'enregistrement des notes.

En charge, voici le corps entier de HTML:

<body> 
    <div id="everything"></div> 
<div class="instance savedNote" id="iddd1b0969-c634-8876-75a9-b274ff87186b" style="top:134px;left:715px;height:30px;">Whatever dude</div> 
<div class="instance savedNote" id="id8a129f06-7d0c-3cb3-9212-0f38a8445700" style="top:131px;left:347px;height:30px;">Appointment 11:45am</div> 
<div class="instance savedNote" id="ide92e3d13-afe8-79d7-bc03-818d4c7a471f" style="top:144px;left:65px;height:80px;">What do you think of a board where you can add writing as much as possible?</div> 
<div class="instance savedNote" id="idef7fe420-4c19-cfec-36b6-272f1e9b5df5" style="top:301px;left:534px;height:30px;">This was submitted</div> 
<div class="instance savedNote" id="id93b3b56f-5e23-1bd1-ddc1-9be41f1efb44" style="top:390px;left:217px;height:30px;">Hello world from iPad.</div> 

</body>

Ma question est donc la suivante: comment puis-je améliorer ce fonctionnement sur iPad?

Je ne suis pas défini sur l'interface utilisateur de jQuery, je me demande si c'est quelque chose que je ne fais pas correctement avec l'interface utilisateur de jQuery ou jQuery, ou s'il existe de meilleurs cadres pour la création d'éléments draggable () multi-plateformes/rétrocompatibles qui fonctionne pour les interfaces utilisateur à écran tactile.

Des commentaires plus généraux sur la façon d'écrire des composants d'interface utilisateur de ce type seraient également les bienvenus.

Merci!


UPDATE: J'ai été capable de simplement chaîner cela sur mon appel jQuery UI draggable() et obtenir la possibilité de glisser correcte sur iPad!

.touch({
    animate: false,
    sticky: false,
    dragx: true,
    dragy: true,
    rotate: false,
    resort: true,
    scale: false
});

Le plugin jQuery Touch a fait le tour!

108
artlung

Après avoir perdu beaucoup d'heures, je suis tombé sur ça!

jquery-ui-touch-punch

Il traduit les événements de tap sous forme d'événements de clic. N'oubliez pas de charger le script après jQuery.

Je travaille sur l'iPad et l'iPhone

$('#movable').draggable({containment: "parent"});
134
ctrl-alt-dileep

Attention: Cette réponse a été écrite en 2010 et la technologie évolue rapidement. Pour une solution plus récente, voir réponse de @ ctrl-alt-dileep ci-dessous .


Selon vos besoins, vous voudrez peut-être essayer le plugin jQuery touch ; vous pouvez essayer un exemple ici . Cela fonctionne bien de glisser sur mon iPhone, contrairement à jQuery UI Draggable.

Alternativement, vous pouvez essayer le plugin this , bien que cela puisse vous obliger à écrire votre propre fonction déplaçable.

Sidenote: Croyez-le ou non, nous entendons de plus en plus entendre dire à quel point les appareils tactiles tels que l'iPad et l'iPhone causent des problèmes à la fois pour les sites Web utilisant des fonctions: survol/sur la souris et du contenu déplaçable.

Si vous êtes intéressé par la solution sous-jacente, utilisez trois nouveaux événements JavaScript. ontouchstart, ontouchmove et ontouchend. Apple a en fait écrit un article sur leur utilisation, que vous pouvez trouver ici . Vous trouverez un exemple simplifié ici . Ces événements sont utilisé dans les deux plugins auxquels j'ai lié.

60
vonconrad

Ce projet devrait être utile: les cartes permettent aux événements tactiles de cliquer sur les événements de manière à ce que l'interface utilisateur de jQuery fonctionne sur iPad et iPhone sans aucune modification. Ajoutez simplement le JS à n’importe quel projet existant.

http://code.google.com/p/jquery-ui-for-ipad-and-iphone/

24
Steve

jQuery ui 1.9 va s'en occuper pour vous. Voici une démo du pré:

https://dl.dropbox.com/u/3872624/lab/touch/index.html

Prenez juste le fichier jquery.mouse.ui.js, collez-le sous le fichier jQuery ui que vous chargez et c’est tout ce que vous devriez avoir à faire! Fonctionne aussi pour le triable.

Ce code fonctionne très bien pour moi, mais si vous rencontrez des erreurs, vous pouvez trouver une version mise à jour de jquery.mouse.ui.js ici:

Jquery-ui sortable ne fonctionne pas sur les appareils tactiles basés sur Android ou IOS

7
thatmiddleway

Ce projet sur github peut être votre solution

https://github.com/furf/jquery-ui-touch-punch

4
boulder_ruby

Je me débattais avec un problème similaire hier. J'avais déjà une solution "de travail" utilisant les interfaces déplaçables de jQuery UI avec jQuery Touch Punch, qui sont mentionnées dans d'autres réponses. Cependant, l’utilisation de cette méthode provoquait pour moi des bugs étranges sur certains appareils Android; c’est pourquoi j’ai décidé d’écrire un petit plugin jQuery qui permet de faire glisser des éléments HTML en utilisant des événements tactiles au lieu d’une méthode qui simule faux. événements de souris.

Le résultat est jQuery Draggable Touch , un simple plug-in jQuery permettant de rendre des éléments déplaçables, dont les périphériques tactiles sont la cible principale à l'aide d'événements tactiles (tels que touchstart, touchmove, touchend, etc.). Il a toujours une solution de repli qui utilise des événements de souris si le navigateur/périphérique ne prend pas en charge les événements tactiles.

2
heyman

Vous pouvez essayer d’utiliser jquery.pep.js :

jquery.pep.js est un plugin léger jQuery qui transforme tout élément DOM en objet déplaçable. Cela fonctionne sur la plupart des navigateurs, de l'ancien au nouveau, du toucher au clic. Je l’ai construit pour répondre à un besoin pour lequel la version déplaçable de jQuery UI ne répondait pas, puisqu’elle ne fonctionnait pas sur les appareils tactiles (sans quelque piratage informatique).

Site Web , lien GitHub

1
martynas