Je veux ajouter automatiquement de nouveaux formulaires à un jeu de formulaires Django à l'aide d'Ajax, de sorte que lorsque l'utilisateur clique sur un bouton "Ajouter", il exécute JavaScript qui ajoute un nouveau formulaire (qui fait partie du jeu de formulaires) à la page.
260
Réponses:
Voici comment je le fais, en utilisant jQuery :
Mon modèle:
Dans un fichier javascript:
Ce qu'il fait:
cloneMore
accepteselector
comme premier argument, ettype
de formset comme 2e argument . Ce qu'ilselector
faut faire, c'est lui transmettre ce qu'il doit reproduire. Dans ce cas, je le passediv.table:last
pour que jQuery recherche la dernière table avec une classe detable
. La:last
partie est importante car leselector
est également utilisé pour déterminer ce que le nouveau formulaire sera inséré après. Il est plus que probable que vous le souhaiteriez à la fin du reste des formulaires. L'type
argument est que nous pouvons mettre à jour lemanagement_form
champ, notammentTOTAL_FORMS
, ainsi que les champs de formulaire réels. Si vous avez un jeu de formulaires rempli, par exemple, deClient
modèles, les champs de gestion auront des ID deid_clients-TOTAL_FORMS
etid_clients-INITIAL_FORMS
, tandis que les champs de formulaire seront au formatid_clients-N-fieldname
avecN
étant le numéro de formulaire, en commençant par0
. Donc , avec l'type
argument de lacloneMore
fonction ressemble à combien de formes Actuellement , il n'y, et passe par chaque entrée et étiquette à l' intérieur du nouveau formulaire remplaçant tous les noms / ids de quelque chose comme champid_clients-(N)-name
àid_clients-(N+1)-name
et ainsi de suite. Une fois terminé, il met à jour leTOTAL_FORMS
champ pour refléter le nouveau formulaire et l'ajoute à la fin de l'ensemble.Cette fonction est particulièrement utile pour moi car la façon dont elle est configurée me permet de l'utiliser dans toute l'application lorsque je veux fournir plus de formulaires dans un jeu de formulaires, et ne me fait pas avoir besoin d'un formulaire "modèle" caché pour dupliquer tant que je lui transmets le nom du jeu de formulaires et le format dans lequel les formulaires sont disposés. J'espère que ça aide.
la source
prefix
membre de l'objet Formset. Cela devrait avoir la même valeur que l'type
argument de lacloneMore
fonction.Version simplifiée de la réponse de Paolo en utilisant
empty_form
comme modèle.la source
CompetitorFormSet = modelformset_factory(ProjectCompetitor, formset=CompetitorFormSets)
ctx['competitor_form_set'] = CompetitorFormSet(request.POST)
je reçois seulement un formulaire, en méthode propre. pouvez-vous expliquer comment traiter cela dans les vues?empty_form
), ce que j'apprécie.J'ai publié un extrait d'une application sur laquelle j'ai travaillé il y a quelque temps. Similaire à Paolo, mais vous permet également de supprimer des formulaires.
la source
La suggestion de Paolo fonctionne à merveille avec une mise en garde - les boutons Précédent / Suivant du navigateur.
Les éléments dynamiques créés avec le script de Paolo ne seront pas rendus si l'utilisateur retourne au jeu de formulaires à l'aide du bouton Précédent / Suivant. Un problème qui peut être une rupture pour certains.
Exemple:
1) L'utilisateur ajoute deux nouveaux formulaires au jeu de formulaires à l'aide du bouton "ajouter plus"
2) L'utilisateur remplit les formulaires et soumet le jeu de formulaires
3) L'utilisateur clique sur le bouton de retour dans le navigateur
4) Formset est maintenant réduit au formulaire d'origine, tous les formulaires ajoutés dynamiquement ne sont pas là
Ce n'est pas du tout un défaut du script de Paolo; mais une réalité avec la manipulation de dom et le cache du navigateur.
Je suppose que l'on pourrait stocker les valeurs du formulaire dans la session et avoir un peu de magie ajax lorsque le formset se charge pour recréer les éléments et recharger les valeurs de la session; mais selon la façon dont vous voulez être anal avec le même utilisateur et plusieurs instances du formulaire, cela peut devenir très compliqué.
Quelqu'un a une bonne suggestion pour faire face à cela?
Merci!
la source
Découvrez les solutions suivantes aux formulaires Django dynamiques:
http://code.google.com/p/django-dynamic-formset/
https://github.com/javisantana/django-dinamyc-form/tree/master/frm
Ils utilisent tous deux jQuery et sont spécifiques à Django. Le premier semble un peu plus soigné et propose un téléchargement avec des démos excellentes.
la source
Simulez et imitez:
<input>
champs.<input>
champs ont changé.Bien que je sache que les jeux de formulaires utilisent des
<input>
champs cachés spéciaux et savent approximativement ce que le script doit faire, je ne me souviens pas des détails du haut de ma tête. Ce que j'ai décrit ci-dessus est ce que je ferais dans votre situation.la source
Il existe un plugin jquery pour cela , je l'ai utilisé avec inline_form défini dans Django 1.3, et cela fonctionne parfaitement, y compris la pré-remplissage, l'ajout, la suppression et la suppression de plusieurs formulaires inline côté client.
la source
Une option consisterait à créer un jeu de formulaires avec tous les formulaires possibles, mais définissez initialement les formulaires non requis sur caché, c'est-à-dire
display: none;
. Lorsqu'il est nécessaire d'afficher un formulaire, définissez son affichage css surblock
ou tout ce qui est approprié.Sans savoir plus de détails sur ce que fait votre "Ajax", il est difficile de donner une réponse plus détaillée.
la source
Une autre version cloneMore, qui permet un nettoyage sélectif des champs. Utilisez-le lorsque vous devez empêcher l'effacement de plusieurs champs.
la source
Il y a un petit problème avec la fonction cloneMore. Puisqu'il nettoie également la valeur des champs cachés générés automatiquement par django, django se plaint si vous essayez d'enregistrer un jeu de formulaires avec plusieurs formulaires vides.
Voici un correctif:
la source
Je pense que c'est une bien meilleure solution.
Comment feriez-vous un jeu de formulaires dynamique dans Django?
Est-ce que les choses clones ne:
la source
Pour que les codeurs qui recherchent des ressources comprennent un peu mieux les solutions ci-dessus:
Django Dynamic Formsets
Après avoir lu le lien ci-dessus, la documentation Django et les solutions précédentes devraient avoir beaucoup plus de sens.
Documentation de Django Formset
Pour résumer rapidement ce qui m'embarrassait: le formulaire de gestion contient un aperçu des formulaires qu'il contient. Vous devez conserver ces informations exactes afin que Django soit au courant des formulaires que vous ajoutez. (Communauté, donnez-moi s'il vous plaît des suggestions si certains de mes mots sont ici. Je suis nouveau à Django.)
la source
@Paolo Bergantino
pour cloner tous les gestionnaires attachés, il suffit de modifier la ligne
pour
pour éviter ce problème.
la source
Oui, je recommanderais également de les afficher en html si vous avez un nombre fini d'entrées. (Si vous ne le faites pas, vous devrez utiliser une autre méthode).
Vous pouvez les masquer comme ceci:
Alors le js est vraiment simple:
la source
Parce que toutes les réponses ci-dessus utilisent jQuery et rendent certaines choses un peu complexes, j'ai écrit le script suivant:
Vous devez d'abord définir auto_id sur false et ainsi désactiver la duplication de l'id et du nom. Étant donné que les noms d'entrée doivent être uniques sous cette forme, toute identification se fait avec eux et non avec des identifiants. Vous devez également remplacer le
form
,type
et le récipient du formset. (Dans l'exemple ci-dessuschoices
)la source