Impossible de sortir du field.change(...) dans le Javascript

Bonjour,

Je constate un comportement étrange lors de l’exécution de la fionction uiField.change(fonction(){…});, et uiField.on(“change”,fonction(){…});

Le but est de remplir des cases nom-adresse-codepostal-ville-siret à l’écran à partir d’une liste de suggestion d’organismes présente dans le field Nom

Le format est le suivant :

  • Nom - Siret - Ville - Code postal - Adresse
    image

Le comportement actuel est le suivant :

Lorsque je tape mon organisme à rechercher, cela fonctionne et me propose la liste, lorsque je sélectionne la liste, l’autocompletion fonctionne.
image
Cependant, lorsque je clique sur n’importe ou sur l’écran, ma fonction d’autocompletion est rapellée, et est appliquée sur ce qu’il reste dans le champ Nom.

Je reste bloqué dans la fonction uiField.change(…) et n’en sort jamais. ( voir console à la fin )
Une parade à cela est d’appuyer sur espace une fois une ligne de la liste de suggestion sélectionnée pour sortir du champ.

Je ne vois pas dans mon code ci-dessous ce qui pourrait causer ce blocage, Est-ce que cela viendrait des différent Hooks qui viendraient perturber ce comportement normalement simple.

Bien cordialement

// LadFormations front side hook

(function(ui) {
    if (!ui) return;
    var app = ui.getAjax();
    // Hook called by each object instance
    Simplicite.UI.hooks.LadFormations = function(o, cbk) {

        		function bindnomorg(ctn,obj) {
        			
            		var idnom = $("#field_ladFormationsNomdelorganisme_idladFormations_LadDossierPmfp_id");
                    var idsiret = $("#field_ladFormationsSiretOrganisme_idladFormations_LadDossierPmfp_id");
                    var idcp = $("#field_ladFormationsCodePostalOrganisme_idladFormations_LadDossierPmfp_id");
                    var idville = $("#field_ladFormationsVilleOrganisme_idladFormations_LadDossierPmfp_id");
                    var idadresse = $("#field_ladFormationsAdressedelorganisme_idladFormations_LadDossierPmfp_id");

                   idnom && idnom.change(function(){
                        console.log("Début du CHANGE");
                        // récupération de la valeur du nom
                        var valNom = idnom.val();
						
                            // récupération du code postal et du siret
                            var chiffres = valNom.replace(/[^0-9\s]/g, '');
                            console.log("Récupération des chiffres", chiffres);
                            chiffres = chiffres.split(' ');
							// rechercher le code postal (5 caractères) et le siret (14 caractères)
                            for (i = 0; i < chiffres.length; i++) {
                                var tmp = chiffres[i];
                                console.log(" longueur : ", chiffres[i].length)
                                if (tmp.length == 5) {
                                    var chainecp = tmp;
                                    console.log("code postal : ", chainecp);
                                } else if (tmp.length == 14) {
                                    var chainesiret = tmp;
                                    console.log("siret : ", chainesiret);
                                }
                            }
                            // récupérer l'index du cp et siret pour séparer la chaine de caractère 
							
                            var indexofCP = valNom.indexOf(chainecp);
                            var indexofSiret = valNom.indexOf(chainesiret);

							// l'adresse se situe après le cp, donc 5 caractères + un espace = le début de l'adresse
                            var chaineadresse = valNom.substring(indexofCP + 6, valNom.length);
							// le nom de la ville se situe après le siret, donc 14 caractères + un espace = le début de la ville
                            var chaineville = valNom.substring(indexofSiret + 15, indexofCP - 1);
							// le nom se situe au début, et s'arrête avant le siret
                            var chainenom = valNom.substring(0, indexofSiret - 1);

							// on parse les valeurs de nos chaines de caractères dans les fields
                            idnom.val(chainenom);
                            idcp.val(chainecp);
                            idsiret.val(chainesiret);
                            idadresse.val(chaineadresse);
                            idville.val(chaineville);
							
			    console.log("Fint du CHANGE");
            			});
        		}


        try {
            console.log("LadFormations hooks loading...");
            var p = o.locals.ui;
            if (p && o.isMainInstance()) {
                p.form.onload = function(ctn, obj) {

                	bindvilleorg(ctn,obj);

                 };
            };

        } catch (e) {
            app.error("Error in Simplicite.UI.hooks.LadFormations: " + e.message);
            console.log("Erreur : ", e.message);
        } finally {
            console.log("LadFormations hooks loaded.");
            cbk && cbk(); // final callback
        }
    };
})(window.$ui);

image

[Platform]
Status=OK
Version=5.1.45

[JavaVM]
Version=17.0.3
Vendor=Eclipse Adoptium
VMName=OpenJDK 64-Bit Server VM
VMVersion=17.0.3+7
ScriptEngine=rhino
ScriptEngineVersion=Rhino 1.7.13 2020 09 02
HeapFree=242343
HeapSize=397312
HeapMaxSize=509952
TotalFreeSize=354983

Bonjour,

Comment est implémentée la completion qui va cherche les résultats concaténés ?
si c’est une datamap Simplicité, il y a effectivement un change qui est déjà bindé, et Simplicité fait déjà la mapping automatiquement des champ du datamap, pas besoin de resplitter à la main.

sinon il y a forcement quelque chose qui boucle, mettez un point d’arret dans votre code (debugger) et au debugger regarder la stack d’appel UI pour retrouver quel traitement se mord la queue.

En jQuery faire un idnom.val(chainenom); ne provoque pas de nouveau change sur le champ.
donc ce n’est pas à ce niveau.

Avez vous des contraintes Front qui positionneraient d’autres changes ?

autres remarques :

comme indiqué dans un post précédent, il faut utiliser getUIField en spécifiant l’index

let idnom = ui.getUIField(ctn,obj,"ladFormationsNomdelorganisme", "ladFormations_LadDossierPmfp_id");

on pourra toujours maintenir une compat ascendante sur les API / accesseur, moins sur les id générés dans cette version.

jQuery ne retourne jamais nul, mais un tableau vide, le test à faire serait plus
idnom.length && idnom.change(...)

mais bon si idnom devient un field UI Simplicité, l’element jQuery est donnée par idnom.ui.input

autre truc peut être à faire, stopper la propagation de l’event change.

idnom.change(function(e) {
   e.stopPropagation();
   // ...
});