elo80ka / django-dynamic-formset

A jQuery plugin that allows you dynamically add new forms to a rendered django formset.
675 stars 309 forks source link

Delete button doesn't get added if the parent row is hidden #107

Open YuriHeupa opened 8 years ago

YuriHeupa commented 8 years ago

I have 2 formsets using this plugin, both are initialized with hidden property, they are conditional, if user presses a option, I change the appropriate formset to visible, but this makes the Delete button not appear, I'm not a JS developer, but I've looked in source code and I found out the problem with this line: https://github.com/elo80ka/django-dynamic-formset/blob/master/src/jquery.formset.js#L138

If I comment this line the Delete button is correctly rendered, because my formset init hidden, and this validation is for visible row, so I got 3 questions: If it's a bug with the plugin, If it's necessary to have this line and what they does?

antrodart commented 5 years ago

I faced the same problem and your issue helped me a lot. I think I managed to do a workaround that solves this without changing or deleting the plugin's source code: First of all, in my template, I have a radio button group that, dynamically, if it evaluates to 0, a new <div> is shown with the formset. If the user changes his opinion and makes the radio button 1, the <div> with the formset logic is hidden. When the page loads, the <div> and formset are initially hidden.

I made a JavaScript function that wraps the plugin's own script in order to call it in others functions: function showFormsetOptions() { $('.option-formset').formset({ addText: 'add option', deleteText: 'remove option', }); } Then, I call this function whenever the initially hidden <div class="editfield"> is shown:

  1. When the page loads with the radio button set to 0: $(document).ready(function () { if ($('input[name=is_binary]:checked', '#market_form').val() === "0") { $('.editfield').show(); showFormsetOptions(); } else $('.editfield').hide(); });

  2. When the user changes the radio button to 0: $('#market_form input[type="radio"]').on('change', function () { if ($('input[name=is_binary]:checked', '#market_form').val() === "1") $('.editfield').hide(); else { $('.editfield').show(); if (!$('.editfield .delete-row').length) { showFormsetOptions(); } } });

Note that, in this last case, when it is the user who changes dynamically if the formset is shown or not, it is necessary to wrap the showFormsetOptions(); caller into an if statement that checks if it is already present in the page, because if that is the case, it will be repeated.