11521 sujets

JavaScript, DOM et API Web HTML5

Bonjour,

Je sais que c'est du "Joe la bricole" mais je n'suis pas doué en javascript.

Je détecte l'événement touche Entrée sur un champ dans lequel l'utilisateur saisit une adresse et j'affiche ainsi l'itinéraire sur une google map.

Comme je n'arrive pas à résoudre un problème de refresh (je redimensionne la carte lorsque j'affiche un itinéraire, et google.maps.event.trigger(map, "resize"); ne détecte pas le redimensionnement du conteneur de ma carte ce qui génère une zone grise), je cherche à simuler la validation du formulaire ou frappe sur touche entrée lorsque l'utilisateur valide le formulaire.
Pour faire simple, mon refresh fonctionne si l'utilisateur tape 2 fois sur la touche entrée. Comme il ne le fera qu'une seule fois, je veux automatiser la seconde fois.

Comment puis-je automatiser ce second "entrée" ?
Bon, comme il est plus intéressant que vous m'appreniez à corriger mes erreurs plutôt qu'à les contourner, j'ai essayé tant bien que mal de faire un codepen avec mon problème de rafraîchissement de carte. Bien entendu, je n'arrive quasiment pas à reproduire l'erreur et vous ne verrez probablement pas de zone grise comme j'ai, peut-être à cause des nombreuses simplifications que j'ai du faire sur le codepen, mais cependant la manière de reproduire mon problème est le suivant :

On tape une ville, on valide, il affiche l'itinéraire. Mais si l'on valide une seconde fois, on s'aperçoit que le centrage se fait à ce moment là et pas avant. Moi bien entendu je voudrais qu'il se fasse sur un seule validation de formulaire.

http://codepen.io/anon/pen/PNgxPr

Ayé : j'ai réussi à reproduire le problème : Vous rafraichissez la page, vous tapez toulouse (ou autre probablement) vous validez, il affiche l'itinéraire mais c'est seulement sur le second valider qu'il zoome et recentre !

Si quelqu'un peut m'aider, je n'trouve pas.

PS : le bandeau noir qui apparaît en haut est normal, il s'agit d'un bandeau que j'affiche uniquement si l'itinéraire est trouvé.
Modifié par Manhattan (15 May 2016 - 10:47)
Salut !
Comeback du we.
Bon je me suis rapidement penché sur ton souci et j'ai l'impression que tu n'étais pas loin, mais les actions ne sont pas appelées dans le bon ordre on va dire...
Le problème est que tu déclenches le "resize" avant la modification du DOM.
                if(status == google.maps.DirectionsStatus.OK){
                    center = map.getCenter();
                    // On redimensionne la carte pour afficher l'itinéraire à côté
                    $('.bandeau').show( 200, function() {
                      $('#ms-map-ctc').addClass('resized-map'); <--tu modifies le DOM ici, 200ms après ton "resize", il faut tout mettre dans ce callback
                    });
                    direction.setDirections(response); // Trace l'itinéraire sur la carte et les différentes étapes du parcours
                    google.maps.event.trigger(map, "resize");
                    map.setCenter(center);
                }

Il faudrait faire comme ça :
                  $('.bandeau').show( 200, function() {
                    direction.setDirections(response);
                    center = map.getCenter();
                    $('#ms-map-ctc').addClass('resized-map');
                    google.maps.event.trigger(map, "resize");
                    map.setCenter(center);
                  });

Un fork ici : http://codepen.io/korell/pen/XdQGyY?editors=0010
Teste et tu me diras si c'est le comportement souhaité.
Modifié par MatthieuR (16 May 2016 - 07:32)
Désolé de t'avoir embêté un we de pentecôte.
Le fork fonctionne exactement comme je veux...
...mais l'adaptation sur mon site non.
Je dois avoir autre chose qui génère cette bande grise...

merci
En fait ton souci est à la ligne suivante :
$('.gm-wrap-ctc').css('height',$(window).height()-160);

Tu n'as pas une transition CSS sur ton height sur cette <div> ?
C'est la seule explication...
Donc soit tu enlèves la transition (?) sur la propriété height, soit tu modifies la hauteur de cette <div> avant ton "resize" (en fait juste avant ton .show(), pas dans son callback). Faut-il encore que la durée de transition soit égale ou inférieure à tes 200ms du .show().

PS : pour remettre dans le contexte pour les lecteurs de ce sujet, Manhattan m'a envoyé le code original par email, c'est pour cela que je peux connaître cette ligne-là...
Modifié par MatthieuR (16 May 2016 - 09:55)
T'es un génie !
Ma p.... de transition css en moins ça le fait achement mieux...

Merci Milllllllllle fois Matthieu Smiley lol
Ah bah ce qu'il faut en retenir, c'est que JS est asynchrone ET capte des infos à un instant T très précis.
D'où l'utilisation des callbacks pour temporiser et maîtriser les actions et que si du appelles une fonction JS en plein milieu d'une modification du DOM (une transition CSS par exemple), ton script te renverra la valeur au moment de l'appel.
Si tu as une transition CSS déclenchée à 0 qui doit aller de 0 à 10 en 100ms, et que tu appelles une fonction JS en même temps tu auras un résultat proche de 0 mais c'est un peu aléatoire et dépendant la vitesse d'exécution de la fonction JS, si elle met 20ms à s'exécuter tu auras une valeur de 2...

Bonne continuation !
Tout à fait. Ptêtre aussi qu'il faudrait que je sois un peu moins ambitieux quant à mes idées ^^

Edit : une ptite dernière question : de ce que je comprends de caniuse concernant calc :
http://caniuse.com/#feat=calc
ie8 et opera mini sont les seuls qui ne le supportent pas.

J'aimerais définir la hauteur de ma carte et de mon panel d’itinéraire ainsi :
height: calc(100vh - 159px);


C'est faisable ? ie8 et opera mini n'auront pas une taille définie puisque je n'ai pas intégré modernizr et tant pis.

Question stupide vu que les mêmes navigateurs ne supportent pas le vh.
Modifié par Manhattan (16 May 2016 - 11:03)