Welcome to the LimeSurvey Community Forum

Ask the community, share ideas, and connect with other LimeSurvey users!

Let users pick values from dropdown and put quantities

  • bianconijo
  • bianconijo's Avatar Topic Author
  • Offline
  • Bronze Donor
  • Bronze Donor
More
1 month 3 weeks ago #258034 by bianconijo
Please help us help you and fill where relevant:
Your LimeSurvey version: 6.4.11+240304
Own server or LimeSurvey hosting: Own server
Survey theme/template: Fruity TwentyThree ( fruity_twentythree )
==================
dear All,
I tried to search in all the forums and faqs but I was unsuccesful to find what I'd need.
I am trying to use Limesurvery to let the participiants pick from a bootstrap dropdown menu one fruit out of 145 fruit types. after picking this fruit, theu need to write how many of this fruit they would pick.
If they want to select a second fruit to pick, they should click on "+" sign to add a line and choose another fruit and quanitty.
and so on, up to 144 lines.
I tried with an array with numbers and customized dropdown (javascript), but I cannot reach something similar.
thanks if anyone can gimme some hints or help.

I remain

BC
Attachments:

Please Log in to join the conversation.

  • Joffm
  • Joffm's Avatar
  • Offline
  • LimeSurvey Community Team
  • LimeSurvey Community Team
More
1 month 3 weeks ago - 1 month 3 weeks ago #258036 by Joffm
Here a rough example (without further css).




Two scripts:
One to dynamically add new rows
One to insert drop downs into an array(text)
For both there are many examples in the forum.

Now it's your turn.
Provide a lss export of your survey (the relevant question(s)).

Might be better to use an autocomplete. I think it to be difficult to search for 145 diferent fruits in a drop down.

Joffm
 

Volunteers are not paid.
Not because they are worthless, but because they are priceless
Last edit: 1 month 3 weeks ago by Joffm.

Please Log in to join the conversation.

  • tpartner
  • tpartner's Avatar
  • Offline
  • LimeSurvey Community Team
  • LimeSurvey Community Team
More
1 month 3 weeks ago #258037 by tpartner
You may want to extend it so the "Add row" button is disabled until both inputs in a given row are populated.

Cheers,
Tony Partner

Solutions, code and workarounds presented in these forums are given without any warranty, implied or otherwise.

Please Log in to join the conversation.

  • bianconijo
  • bianconijo's Avatar Topic Author
  • Offline
  • Bronze Donor
  • Bronze Donor
More
1 month 3 weeks ago #258038 by bianconijo
Thanks Joffm, I have been trying with no success till now. But I'll try again, using different scripts (I picked the most recent).

Yes, Tony, that would be great.
But first I need to make it work the basic version (no autocomplete and "Add row" button disabled until both fields are populted).

Thanks,

BC

Please Log in to join the conversation.

  • tpartner
  • tpartner's Avatar
  • Offline
  • LimeSurvey Community Team
  • LimeSurvey Community Team
More
1 month 3 weeks ago #258039 by tpartner
This workaround will insert your "Add row" buttons in LS6.x - manual.limesurvey.org/Workarounds:_Manip...meSurvey_version_6.x

Cheers,
Tony Partner

Solutions, code and workarounds presented in these forums are given without any warranty, implied or otherwise.

Please Log in to join the conversation.

  • tpartner
  • tpartner's Avatar
  • Offline
  • LimeSurvey Community Team
  • LimeSurvey Community Team
More
1 month 3 weeks ago - 1 month 3 weeks ago #258043 by tpartner
Here is a script that, when placed in the source of an array(texts) question, should handle all of your requirements:
- Insert a drop-down in column 1
- Apply the "Variable length array" workaround linked above
- Disable the "Add row" button unless both inputs in the last visible row are populated

Code:
<script type="text/javascript" data-author="Tony Partner">
 
    $(document).on('ready pjax:scriptcomplete',function(){
 
        // Identify this question
        var thisQuestion = $('#question{QID}');
 
        // Index the array columns
        $('table.subquestion-list tr', thisQuestion).each(function(i) {
            $('> *', this).each(function(i) {
                $(this).attr('data-index', i);
            });
        });
 
        // Define the dropdown
        var select1 = '<select class="form-select form-control list-question-select inserted-select">\
                <option value="">Please choose...</option>\
                <option value="A1">Apples</option>\
                <option value="A2">Bananas</option>\
                <option value="A3">Cherries</option>\
                <option value="A4">Dates</option>\
                <option value="A5">Elderberries</option>\
            </select>'
 
        // Hide the column-1 text inputs
        $('.answer-item[data-index="1"] :text', thisQuestion).addClass('d-none');
 
        // Insert the column-1 dropdowns
        $('.answer-item[data-index="1"]', thisQuestion).append(select1);
 
        // Listener on the dropdowns
        $('.inserted-select', thisQuestion).on('change', function(e) {
            var thisCell = $(this).closest('.answer-item');
            $(':text', thisCell).val($(this).val()).trigger('keyup');
        });
 
        // Returning to the page
        $('.inserted-select', thisQuestion).each(function(i) {
            var thisCell = $(this).closest('.answer-item');
            $(this).val($(':text', thisCell).val());
        }); 
 
        // A function to add or remove rows of an Array (Multi Flexible)(Text) question
        function varLengthArray(thisQuestion) {
 
            if ($(thisQuestion).length > 0) {
 
                // The HTML content of the Add/Remove elements - modify as you wish
                var addContent = '[+] Add row';
                var removeContent = '[-] Remove row';
 
                // The classes for the Add/Remove elements - modify as you wish
                // See https://getbootstrap.com/docs/5.0/getting-started/introduction/
                var addClasses = 'inserted-button add btn btn-success';
                var removeClasses = 'inserted-button remove btn btn-danger';
 
                // The styles for the Add/Remove elements - modify as you wish
                // These could be placed in your custom.css file.
                var addStyles = 'margin:10px 0 10px 10px; padding:1px 5px; text-align:center; width:auto; cursor:pointer; float:left;';
                var removeStyles = 'margin:10px 0 10px 10px; padding:1px 5px; text-align:center; width:auto; cursor:pointer; float:left;';
 
                // Insert the buttons
                $( 'table.ls-answers', thisQuestion).after('<div class="button-wrapper">\
                        <button type="button" class="'+addClasses+'" style="'+addStyles+'">'+addContent+'</button>\
                        <button type="button" class="'+removeClasses+'" style="display: none; '+removeStyles+'">'+removeContent+'</button>\
                    </div>');
 
                // Listeners on the buttons
                $('.inserted-button.add', thisQuestion).on('click', function (event) {
                    addRow();
                });
                $('.inserted-button.remove', thisQuestion).on('click', function (event) {
                    removeRow();
                });
 
                // Define the relevant rows
                var relevantRows = $('tr.subquestion-list:not(.ls-irrelevant)', thisQuestion);
 
                // Function to add a row, show the "Remove" element and hide the "Add" element if all rows are shown
                function addRow() {
                    $('[data-visible="false"]:first', thisQuestion).attr('data-visible', 'true').show();
                    $('.inserted-button.remove', thisQuestion).show();
                    if ($('[data-visible="false"]', thisQuestion).length == 0)  {
                        $('.inserted-button.add', thisQuestion).hide();
                    }
                    $('.inserted-button.add', thisQuestion).blur();
 
                    handleAddButton();
                }
 
                // Function to remove a row, clear the contents of the removed row,
                // show the "Add" element if the last row is hidden and hide the "Remove" element if only the first row is shown
                function removeRow() {
                    $('[data-visible="true"]:last input:text', thisQuestion).val('').trigger('keyup');
                    $('[data-visible="true"]:last select', thisQuestion).val('');
                    $('[data-visible="true"]:last', thisQuestion).attr('data-visible', 'false').hide();
                    $('.inserted-button.add', thisQuestion).show();
                    if ($('[data-visible="true"]', thisQuestion).length == 0)  {
                        $('.inserted-button.remove', thisQuestion).hide();
                    }
                    $('.inserted-button.remove', thisQuestion).blur();
 
                    handleAddButton();
                }
 
                // Initially hide all except first row or any rows with populated inputs
                $(relevantRows).slice(1).each(function(i) {
                    $( this ).attr('data-visible', 'false').hide();
 
                    $('input[type=text]', this).each(function(i) {
                        if ($.trim($(this).val()) != '') {
                            $(this).closest('tr').attr('data-visible', 'true').show();
                            $('.inserted-button.remove', thisQuestion).show();
                        }
                    });
                });
            }
 
            // Function handle the "Add row" button
            function handleAddButton() {
               var lastRow = $('tr[id^="javatbd"]:visible:last', thisQuestion);
                var emptyInputs = $(':text.form-control', lastRow).filter(function() {
                    return $.trim($(this).val()) == '';
                });
                if(emptyInputs.length > 0) {
                    $('.inserted-button.add', thisQuestion).prop('disabled', true);
                }
                else {
                    $('.inserted-button.add', thisQuestion).prop('disabled', false);
                }
            }
 
            // Initial "Add row" state
            handleAddButton();
 
            // Listeners for the "Add row" state
            $(':text.form-control, .inserted-select', thisQuestion).on('keyup change', function(e) {
                handleAddButton();
            });
        }
 
        // Apply the variable-length array
        varLengthArray(thisQuestion);
 
    });
</script>

Sample survey attached: 

File Attachment:

File Name: limesurvey...3-04.lss
File Size:42 KB

Cheers,
Tony Partner

Solutions, code and workarounds presented in these forums are given without any warranty, implied or otherwise.
Last edit: 1 month 3 weeks ago by tpartner.

Please Log in to join the conversation.

  • bianconijo
  • bianconijo's Avatar Topic Author
  • Offline
  • Bronze Donor
  • Bronze Donor
More
1 month 3 weeks ago - 1 month 3 weeks ago #258044 by bianconijo
dear Tony, thank you very much for your support. I remember you also helped me more than 10 years ago when I was in need.
so i dont want to bother you and your community.
is there a way to make the dropdown endowed with the autocomplete function? I am asking because the values to pick are 145.
I am trying to put this script in your script but no success for the moment:<script type="text/javascript" charset="utf-8">

$(document).ready(function() {

var qID = 1;

$('#question'+qID+' input[type="text"]').autocomplete({
minLength: 2, // This line is optional, signifies number of keystrokes before autocomplete is initiated
source: ["Test1","Test2","Test3"]
});

});

</script>

Thanks again,

BC
Last edit: 1 month 3 weeks ago by bianconijo.

Please Log in to join the conversation.

  • Joffm
  • Joffm's Avatar
  • Offline
  • LimeSurvey Community Team
  • LimeSurvey Community Team
More
1 month 3 weeks ago #258049 by Joffm
Though I am not addressed, here an answer.
Yes, it's easy
Code:
<link href="//code.jquery.com/ui/1.12.1/themes/base/jquery-ui.css" rel="stylesheet" />
<script src="https://code.jquery.com/ui/1.12.1/jquery-ui.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery-csv/1.0.11/jquery.csv.min.js">
 
</script><script type="text/javascript" charset="utf-8">
  $(document).on('ready pjax:complete',function() {
    var url = "/lime6/upload/surveys/{SID}/files/namen.csv";
 
    var Names = new Array();
 
    $.get(url,function(data){
      fullArray = $.csv.toArrays(data);
      $(fullArray).each(function(i, item){
        Names.push(item[0]);
      });
      $('#question{QID} .answer-item:nth-child(2) input[type="text"]').autocomplete({
        minLength: 2,
        source: Names
      });
    });
  });
</script>
Here the names are in a csv-file.
But you also may use an array.





There is a better (javascript) solution to avoid duiplicates than the simple validation.
Of course, Tony provided it a few years ago, but only for "multiple short text"

Joffm
 

Volunteers are not paid.
Not because they are worthless, but because they are priceless

Please Log in to join the conversation.

  • bianconijo
  • bianconijo's Avatar Topic Author
  • Offline
  • Bronze Donor
  • Bronze Donor
More
1 month 3 weeks ago #258052 by bianconijo
hello Joff, your suggestions are very welcome!
I've tried to paste your code within Tony's script in different positions, but I dont know where to put exactly to make it work.
I just put the csv in a folder on the server and changed the releted path in the script.
thanks again.

BC

Please Log in to join the conversation.

  • tpartner
  • tpartner's Avatar
  • Offline
  • LimeSurvey Community Team
  • LimeSurvey Community Team
More
1 month 3 weeks ago - 1 month 3 weeks ago #258054 by tpartner
When using autocomplete on a text input, it is tricky to force a selection from the data set.

Given the relatively small data set (145 items), I would be inclined to use drop-downs and add searching with the Select2 platform - select2.org/

So, the modified code:

Code:
<link href="https://cdn.jsdelivr.net/npm/select2@4.1.0-rc.0/dist/css/select2.min.css" rel="stylesheet" />
<script src="https://cdn.jsdelivr.net/npm/select2@4.1.0-rc.0/dist/js/select2.min.js"></script>
<script type="text/javascript" data-author="Tony Partner">
 
    $(document).on('ready pjax:scriptcomplete',function(){
 
        // Identify this question
        var thisQuestion = $('#question{QID}');
 
        // Index the array columns
        $('table.subquestion-list tr', thisQuestion).each(function(i) {
            $('> *', this).each(function(i) {
                $(this).attr('data-index', i);
            });
        });
 
        // Define the dropdown
        var select1 = '<select class="form-select form-control list-question-select inserted-select">\
                <option value="">Please choose...</option>\
                <option value="A1">Apples</option>\
                <option value="A2">Bananas</option>\
                <option value="A3">Cherries</option>\
                <option value="A4">Dates</option>\
                <option value="A5">Limes</option>\
                <option value="A6">Nectarines</option>\
                <option value="A7">Plumbs</option>\
                <option value="A8">Elderberries</option>\
                <option value="A9">Lemons</option>\
                <option value="A10">Peaches</option>\
                <option value="A11">Blueberries</option>\
                <option value="A12">Grapes</option>\
            </select>'
 
        // Define the placeholder text for the select2 search input
        var placeholder = 'Type here to search the dropdown';
 
        // Hide the column-1 text inputs
        $('.answer-item[data-index="1"] :text', thisQuestion).addClass('d-none');
 
        // Insert the column-1 dropdowns
        $('.answer-item[data-index="1"]', thisQuestion).append(select1);
 
        // Listener on the dropdowns
        $('.inserted-select', thisQuestion).on('change', function(e) {
            var thisCell = $(this).closest('.answer-item');
            $(':text', thisCell).val($(this).val()).trigger('keyup');
        });
 
        // Returning to the page
        $('.inserted-select', thisQuestion).each(function(i) {
            var thisCell = $(this).closest('.answer-item');
            $(this).val($(':text', thisCell).val());
        }); 
 
        // Initiate the select2 search function
        $('.inserted-select', thisQuestion).select2();
        $('.inserted-select', thisQuestion).on('select2:open', function(e) {
            document.querySelector('.select2-search__field').focus();
            $('input.select2-search__field').prop('placeholder', placeholder);
        });
 
        // A function to add or remove rows of an Array (Multi Flexible)(Text) question
        function varLengthArray(thisQuestion) {
 
            if ($(thisQuestion).length > 0) {
 
                // The HTML content of the Add/Remove elements - modify as you wish
                var addContent = '[+] Add row';
                var removeContent = '[-] Remove row';
 
                // The classes for the Add/Remove elements - modify as you wish
                // See https://getbootstrap.com/docs/5.0/getting-started/introduction/
                var addClasses = 'inserted-button add btn btn-success';
                var removeClasses = 'inserted-button remove btn btn-danger';
 
                // The styles for the Add/Remove elements - modify as you wish
                // These could be placed in your custom.css file.
                var addStyles = 'margin:10px 0 10px 10px; padding:1px 5px; text-align:center; width:auto; cursor:pointer; float:left;';
                var removeStyles = 'margin:10px 0 10px 10px; padding:1px 5px; text-align:center; width:auto; cursor:pointer; float:left;';
 
                // Insert the buttons
                $( 'table.ls-answers', thisQuestion).after('<div class="button-wrapper">\
                        <button type="button" class="'+addClasses+'" style="'+addStyles+'">'+addContent+'</button>\
                        <button type="button" class="'+removeClasses+'" style="display: none; '+removeStyles+'">'+removeContent+'</button>\
                    </div>');
 
                // Listeners on the buttons
                $('.inserted-button.add', thisQuestion).on('click', function (event) {
                    addRow();
                });
                $('.inserted-button.remove', thisQuestion).on('click', function (event) {
                    removeRow();
                });
 
                // Define the relevant rows
                var relevantRows = $('tr.subquestion-list:not(.ls-irrelevant)', thisQuestion);
 
                // Function to add a row, show the "Remove" element and hide the "Add" element if all rows are shown
                function addRow() {
                    $('[data-visible="false"]:first', thisQuestion).attr('data-visible', 'true').show();
                    $('.inserted-button.remove', thisQuestion).show();
                    if ($('[data-visible="false"]', thisQuestion).length == 0)  {
                        $('.inserted-button.add', thisQuestion).hide();
                    }
                    $('.inserted-button.add', thisQuestion).blur();
 
                    handleAddButton();
                }
 
                // Function to remove a row, clear the contents of the removed row,
                // show the "Add" element if the last row is hidden and hide the "Remove" element if only the first row is shown
                function removeRow() {
                    $('[data-visible="true"]:last input:text', thisQuestion).val('').trigger('keyup');
                    $('[data-visible="true"]:last select', thisQuestion).val('');
                    $('[data-visible="true"]:last', thisQuestion).attr('data-visible', 'false').hide();
                    $('.inserted-button.add', thisQuestion).show();
                    if ($('[data-visible="true"]', thisQuestion).length == 0)  {
                        $('.inserted-button.remove', thisQuestion).hide();
                    }
                    $('.inserted-button.remove', thisQuestion).blur();
 
                    handleAddButton();
                }
 
                // Initially hide all except first row or any rows with populated inputs
                $(relevantRows).slice(1).each(function(i) {
                    $( this ).attr('data-visible', 'false').hide();
 
                    $('input[type=text]', this).each(function(i) {
                        if ($.trim($(this).val()) != '') {
                            $(this).closest('tr').attr('data-visible', 'true').show();
                            $('.inserted-button.remove', thisQuestion).show();
                        }
                    });
                });
            }
 
            // Function handle the "Add row" button
            function handleAddButton() {
               var lastRow = $('tr[id^="javatbd"]:visible:last', thisQuestion);
                var emptyInputs = $(':text.form-control', lastRow).filter(function() {
                    return $.trim($(this).val()) == '';
                });
                if(emptyInputs.length > 0) {
                    $('.inserted-button.add', thisQuestion).prop('disabled', true);
                }
                else {
                    $('.inserted-button.add', thisQuestion).prop('disabled', false);
                }
            }
 
            // Initial "Add row" state
            handleAddButton();
 
            // Listeners for the "Add row" state
            $(':text.form-control, .inserted-select', thisQuestion).on('keyup change', function(e) {
                handleAddButton();
            });
        }
 
        // Call the function with a question ID
        varLengthArray(thisQuestion);
 
    });
</script>

 

Sample survey attached:  

File Attachment:

File Name: limesurvey...3981.lss
File Size:43 KB


 

Cheers,
Tony Partner

Solutions, code and workarounds presented in these forums are given without any warranty, implied or otherwise.
Last edit: 1 month 3 weeks ago by tpartner.

Please Log in to join the conversation.

  • Joffm
  • Joffm's Avatar
  • Offline
  • LimeSurvey Community Team
  • LimeSurvey Community Team
More
1 month 3 weeks ago #258056 by Joffm
Oh, that's great to have a searchable dropdown here.
Thanks

Joffm

Volunteers are not paid.
Not because they are worthless, but because they are priceless

Please Log in to join the conversation.

  • bianconijo
  • bianconijo's Avatar Topic Author
  • Offline
  • Bronze Donor
  • Bronze Donor
More
1 month 3 weeks ago #258079 by bianconijo
Thanks Tony: your solution works a charm!
And thanks Joffm for your suggestions.
LM and its community are the best!

BC

Please Log in to join the conversation.

Lime-years ahead

Online-surveys for every purse and purpose