AngularJS navigateur remplissage automatique de la solution en utilisant une directive
Lors de la soumission d'un formulaire dans AngularJS et d'utiliser le navigateur de mémoriser le mot de passe de la fonctionnalité, et lors d'une tentative de connexion vous laisser le navigateur de remplir le formulaire de connexion avec le nom d'utilisateur et le mot de passe, le $scope
modèle ne sera pas modifié sur la base de remplissage automatique.
La seule sale hack que j'ai trouvé est d'utiliser la directive suivante:
app.directive("xsInputSync", ["$timeout" , function($timeout) {
return {
restrict : "A",
require: "?ngModel",
link : function(scope, element, attrs, ngModel) {
$timeout(function() {
if (ngModel.$viewValue && ngModel.$viewValue !== element.val()) {
scope.apply(function() {
ngModel.$setViewValue(element.val());
});
}
console.log(scope);
console.log(ngModel.$name);
console.log(scope[ngModel.$name]);
}, 3000);
}
};
}]);
Le problème est que le ngModel.$setViewValue(element.val());
ne change pas le modèle ni la vue basée sur la element.val()
la valeur retournée. Comment puis-je le réaliser?
Ce code semble correct à première vue... mais où est le reste (balisage, etc)? Avez-vous un violon ou plunk nous pouvons voir?
Voici le plunk: plnkr.co/modifier/CHrBAVU9Ycl2ex2DRr6R je ne sais pas si il fonctionne directement sur plunker parce qu'il fonctionne dans un iframe.
Vous n'avez pas besoin à portée.$appliquer à l'intérieur angulaire de $timeout. Vous pourriez en avoir besoin à l'intérieur de fenêtre native.setTimeout. Mais c'est une bonne idée d'utiliser angulaire.
Il y a un "officiel" polyfill fix Angulaires dev tbosch pour ce problème. Veuillez voir les détails dans la réponse stackoverflow.com/a/25687396/3009639 ci-dessous.
Malheureusement, les "officiels" fix est abandonware et ne fonctionne pas dans la plupart des navigateurs. Les questions ont été déposés, mais ne sont pas pris en compte jusqu'à la recherche continue...
Voici le plunk: plnkr.co/modifier/CHrBAVU9Ycl2ex2DRr6R je ne sais pas si il fonctionne directement sur plunker parce qu'il fonctionne dans un iframe.
Vous n'avez pas besoin à portée.$appliquer à l'intérieur angulaire de $timeout. Vous pourriez en avoir besoin à l'intérieur de fenêtre native.setTimeout. Mais c'est une bonne idée d'utiliser angulaire.
Il y a un "officiel" polyfill fix Angulaires dev tbosch pour ce problème. Veuillez voir les détails dans la réponse stackoverflow.com/a/25687396/3009639 ci-dessous.
Malheureusement, les "officiels" fix est abandonware et ne fonctionne pas dans la plupart des navigateurs. Les questions ont été déposés, mais ne sont pas pris en compte jusqu'à la recherche continue...
OriginalL'auteur lucassp | 2013-02-19
Vous devez vous connecter pour publier un commentaire.
Apparemment c'est un problème connu avec Angulaires et est actuellement ouvert
Je ne suis pas sûr de ce que vous pourriez faire ici à part une sorte de travail autour de vous comme vous êtes à essayer. Il semble que vous êtes sur la bonne voie. Je ne pouvais pas obtenir mon navigateur pour essayer de vous souvenir d'un mot de passe pour votre plunk, donc je ne suis pas sûr si cela va fonctionner, mais regardez:
Je pense que vous avez juste besoin de simplifier votre approche un peu. La seule chose que je vous recommande vraiment de est de vérifier
ngModel.$pristine
et assurez-vous que vous n'êtes pas d'écraser le pauvre utilisateur d'entrée. Aussi, 3 secondes est probablement trop long. Vous ne devriez pas avoir à appeler $apply () $timeout, BTW, il devrait mettre un $digest automatiquement pour vous.Le vrai catch: votre navigateur battre Angulaire de l'exécution? Mon navigateur?
C'est probablement une guerre impossible à gagner, c'est pourquoi Angulaire (ou knock-out) n'a pas été en mesure de le résoudre facilement. Il n'y a aucune garantie de l'état des données dans votre entrée au moment de la directive de l'exécution initiale. Pas même au moment de l'Angulaire de l'initialisation.... C'est donc un problème difficile à résoudre.
Juste le tromper avec le stockage local. 🙂 ... Je vais continuer à penser à elle. Mais j'ai des doutes sur la faisabilité de la prise de remplissage automatique de travail avec toutes les liaisons bidirectionnelles.
Oui, mais j'ai encore besoin pour être en mesure de mettre à jour le modèle à partir d'une directive pour que cela fonctionne.
J'a fait une blague à propos de localStorage, vous ne voulez pas conserver les mots de passe.
Cela ne fonctionne pas avec Safari et de la carte bancaire saisie semi-automatique, que ce remplissage automatique est déclenché à tout moment par l'utilisateur
OriginalL'auteur Ben Lesh
Voici une solution qui est beaucoup moins hacky que les autres solutions présentées et est sémantiquement son AngularJS: http://victorblog.com/2014/01/12/fixing-autocomplete-autofill-on-angularjs-form-submit/
Ensuite il vous suffit de fixer la directive à votre formulaire:
Ce n'est plus de travail pour moi (sans jQuery)
Comme il utilise jQuery, il n'est pas prévu pour fonctionner sans jQuery.
Ici, nous sommes en 2018, et c'est encore le correctif. Grâce Ezéchiel!
OriginalL'auteur Ezekiel Victor
Vous n'avez pas à utiliser un
$timeout
ou quelque chose comme cela. Vous pouvez utiliser un système d'événements.Je pense que c'est plus Angularish et ne dépend pas de jQuery ou d'un événement personnalisé attraper.
Par exemple sur votre gestionnaire de soumission:
Et puis vous pouvez avoir une
autofill
directive comme ceci:Enfin, votre code HTML sera comme:
ne jamais vous avez des problèmes avec ce qu'il est asynchrone? où la connexion d'appel au serveur déjà les feuilles avant l'événement a été reproduite et la directive eu le temps de mettre à jour le champ d'application?
OriginalL'auteur bekos
Sale code, vérifier si le problème https://github.com/angular/angular.js/issues/1460#issuecomment-18572604 est fixé avant d'utiliser ce code.
Cette directive déclenche des événements lorsque le champ est rempli, non seulement avant de soumettre (il est nécessaire si vous avez à gérer l'entrée avant de soumettre)
OriginalL'auteur OZ_
Pas besoin de hack plus! Angulaire dev tbosch fait un polyfill qui déclenche un événement de changement lorsque le navigateur changements de champs de formulaire sans le déclenchement d'un événement de changement:
https://github.com/tbosch/autofill-event
Pour l'instant ils ne sont pas dans l'angle de code, comme c'est une correction de bug pour le navigateur, et fonctionne aussi sans Angulaire (par exemple, pour la plaine de jQuery apps).
"Le polyfill va rechercher les modifications sur le document de charge et également lorsqu'une entrée est à gauche (dans la même forme). Cependant, vous pouvez déclencher le vérifier manuellement si vous le souhaitez.
Le projet a des tests unitaires ainsi que des semi automatique de tests, de sorte que nous avons enfin un endroit pour rassembler tous les différents cas d'utilisation, de concert avec les paramètres du navigateur.
Veuillez noter: Ce polyfill fonctionne avec la plaine AngularJS apps, avec AngularJS/jQuery applications, mais aussi avec la plaine jQuery applications qui n'utilisent pas Angulaire."
Il peut être installé:
Ajouter le script
autofill-event.js
après jQuery ou Angulaire dans votre page.Cela va faire ce qui suit:
API (pour déclencher manuellement la case):
$el.checkAndTriggerAutoFillEvent()
: Exécuter la vérification de tous les éléments du DOM dans le jQuery /jQLite élément.Comment il fonctionne
Rappelez-vous toutes les modifications apportées aux éléments d'entrée par l'utilisateur (à l'écoute des événements de changement) et aussi par JavaScript (en interceptant $el.val() de jQuery /jQLite éléments). Qui a changé la valeur est stockée sur l'élément dans une propriété privée.
Vérification d'un élément de remplissage automatique: Comparer la valeur actuelle de l'élément avec la rappeler valeur. Si c'est différent, déclencher un événement de changement.
Dépendances
AngularJS ou jQuery (fonctionne avec l'un ou les deux)
Plus d'infos et source sur le page github.
D'origine Angulaire de la Question n ° 1460 sur Github peut être lu ici.
Je n'ai pas eu de problèmes à l'aide de cette polyill. Si vous ne pouvez pas l'obtenir pour fonctionner correctement, vous devez créer une question distincte, y compris une partie du code. Si vous trouvez un bug, vous devriez vérifier les billets sur github, ou en ouvrir un nouveau.
Yep, je pense que c'est lié à ce bug: github.com/tbosch/autofill-event/issues/11
ne fonctionne pas pour moi sur Chrome
ngModelOptions
combiné avecautofill-event
signifie que vous pouvez maintenant spécifierchange
comme l'un desupdateOn
événements pour s'assurer que le modèle est correctement synchronisé.OriginalL'auteur orszaczky
Semble claire comme du droit de l'avant de la solution. Pas de jQuery nécessaire.
Mise à JOUR:
valeur.
un autre compte par exemple.
$pristine
avant de le changer, et puis après l'avoir modifié en garder$pristine
état. Sinon, vous trouverez que si un formulaire est chargé avec pas de saisie automatique des données, la directive ci-dessus sera encore de mise à jour du modèle et par la suite ildirty
même si le contrôle de formulaire doit être toujours considéré comme intact. exemple ici, à l'aide de votre directive. J'ai commenté le code, je voudrais ajouter: jsfiddle.net/OACDesigns/L8Sja/4aussi, je pense que
scope:true
devrait êtrescope:{}
OriginalL'auteur gorpacrate
Solution 1 [à l'Aide de $timeout]:
Directive:
HTML:
Solution 2 [Aide angulaire des événements]:
Ref: Becko réponse
Directive:
HTML:
Solution 3 [à l'Aide de relais des appels de méthode]:
Directive:
HTML:
Le numéro 1 a travaillé, numéro 2 n'a pas.
Solution 1 a fonctionné très bien pendant un certain temps, mais maintenant, sur angularjs 1.4.9 il ne fonctionne plus. La vérification de
model.$valid
dans la directive renvoie la valeur true à la fois avant et après$setViewValue
, mais l'élément est toujours avecng-invalid
classeOriginalL'auteur Robin Rizvi
Bien, la façon la plus simple c'est d'émuler le comportement du navigateur, donc si il ya un problème avec le changement de l'événement, il suffit de le lancer vous-même. Beaucoup plus simple.
Directive:
HTML:
Vous pouvez faire des variations, comme de mettre la directive sur la forme et le tir de l'événement sur toutes les entrées avec le .sale de classe sur le formulaire de soumission.
OriginalL'auteur pedroassis
C'est jQuery façon :
C'est Angulaire moyen :
HTML
Maintenant, vérifiez auprès angulaire.
L'angle Moyen de languettes ont trop d'espaces. Juste de rigolade. J'aime le défilement horizontal.
très drôle , mais c'est tellement facile à lire .
triggerHandler('input')
devrait être ok si vous n'avez pas complet soufflé jqueryOriginalL'auteur Nishchit Dhanani
Voici une autre solution qui est moins hacky, mais exige un peu de code dans le contrôleur.
HTML:
Directive (CoffeeScript):
Contrôleur:
CoffeeScript.org fournit un traducteur: ici
OriginalL'auteur jab
C'est la seule solution que j'ai trouvé qui a permis à tous de mon Angulaire' validations de fonctionner comme prévu, y compris désactiver/activer de bouton soumettre. S'installe avec tonnelle et 1 balise de script. Bazinga!
https://github.com/tbosch/autofill-event
OriginalL'auteur Roland Hordos
La modification de la valeur de modèle, au lieu d'utiliser une fonction de délai a fonctionné pour moi.
Voici mon code:
OriginalL'auteur Swaron Chen
One-liner solution de contournement dans le gestionnaire de soumission (nécessite jQuery):
OriginalL'auteur archpollux
Je force un $setValue(val()) sur soumettre: (cela fonctionne sans jQuery)
OriginalL'auteur malix
Je suis très nouveau à Angularjs, mais j'ai trouvé une solution simple à ce problème=>
Force Angulaire de réévaluer expression... en changeant de!
(bien sûr, vous devez vous rappeler la valeur initiale pour revenir à l'état initial)
Ici est la façon dont il va dans votre fonction de contrôleur de soumission du formulaire:
où bien sûr, la valeur entrée dans votre mot de passe d'entrée a été fixé par les fenêtres et pas par l'utilisateur.
OriginalL'auteur Le neveu
Vous pouvez essayer ce code :
OriginalL'auteur Rohit
Une modification mineure à la présente réponse (https://stackoverflow.com/a/14966711/3443828): utiliser un $intervalle au lieu de $timeout de sorte que vous n'avez pas de course le navigateur.
OriginalL'auteur user3443828
C'est la solution que j'ai fini par utiliser dans mes formulaires.
Et la forme du modèle sera
De cette façon, j'ai été capable d'exécuter des analyseurs/formateurs que j'ai sur mon ng-model et avoir la soumission de la fonctionnalité transparent.
OriginalL'auteur Anirudhan J
Solution sans directives:
OriginalL'auteur ReklatsMasters
C'est une solution simple qui fonctionne pour tous les cas je l'ai testé dans Firefox et Chrome. Notez qu'avec le haut de réponse (directive w/timeout) j'ai eu des problèmes avec la -
Ce correctif est évidemment très bête et hacky, mais il fonctionne 100% du temps -
$timeout
avec$interval
à donner aux futurs développeurs un peu plus de contexte et de se débarrasser de l'étrange à la recherche d'appels récursifs se passe là-basOriginalL'auteur Richard Nichols
Aucune de ces solutions n'a fonctionné pour mon cas d'utilisation. J'ai certains champs du formulaire qui utilisent ng-changement de regarder pour le changement. À l'aide de
$watch
n'est d'aucun secours car il n'est pas déclenché par le remplissage automatique. Depuis je n'ai pas de bouton "soumettre" il n'est pas facile à exécuter certaines des solutions et je n'ai pas réussi à l'aide d'intervalles.J'ai fini par désactiver la saisie automatique - pas idéal, mais beaucoup moins à confusion pour l'utilisateur.
Trouvé la réponse ici
OriginalL'auteur cyberwombat
Si vous utilisez jQuery, vous pouvez le faire sur le formulaire de soumettre:
HTML:
JS:
OriginalL'auteur Hans Kerkhof
Si vous voulez le garder simple il suffit d'obtenir la valeur à l'aide de javascript
Dans votre angular js contrôleur :
var username = document.getElementById('username').valeur;
OriginalL'auteur user361697