2

How can I randomize the Answers(shuffle options order ) in the google forms programatically using google app script?.

There are methods available to set points, set required option in the forms but is there any methods available to shuffle answers.

My sample code as for now:-

var quest = SpreadsheetApp.getActiveSheet().getRange(1,4).getValue();
var ans1 = SpreadsheetApp.getActiveSheet().getRange(1,4).getValue();
var ans2 = SpreadsheetApp.getActiveSheet().getRange(1,5).getValue();
var ans3 = SpreadsheetApp.getActiveSheet().getRange(1,6).getValue();
var ans4 = SpreadsheetApp.getActiveSheet().getRange(1,9).getValue();


 var item = form.addMultipleChoiceItem();
 item.setChoices([
 item.createChoice(ans1, false),
 item.createChoice(ans2, false),
 item.createChoice(ans3, false),
 item.createChoice(ans4, true),    
]);

  item.setTitle(quest)
  item.setRequired(true);
  item.setPoints(1);

EDIT: IMPLEMENTED SOLUTION

I have implemented with below logic for my aforesaid question and it worked. I hope it may help others too. Below is the code snippet

var quest = SpreadsheetApp.getActiveSheet().getRange(2,3).getValue();   
var ans1 = SpreadsheetApp.getActiveSheet().getRange(2,4).getValue();
var ans2 = SpreadsheetApp.getActiveSheet().getRange(2,5).getValue();
var ans3 = SpreadsheetApp.getActiveSheet().getRange(2,6).getValue();
var ans4 = SpreadsheetApp.getActiveSheet().getRange(2,7).getValue();
var correctans = SpreadsheetApp.getActiveSheet().getRange(2,8).getValue();
var  item = form.addMultipleChoiceItem();
item.setTitle(quest);

if (ans1 == correctans){
item.setChoices([item.createChoice(ans1, true),item.createChoice(ans2,false),item.createChoice(ans3,false),item.createChoice(ans4,false)]);};
    if (ans2 == correctans){
item.setChoices([item.createChoice(ans1, false),item.createChoice(ans2,true),item.createChoice(ans3,false),item.createChoice(ans4,false)]);};
    if (ans3 == correctans){
item.setChoices([item.createChoice(ans1, false),item.createChoice(ans2,false),item.createChoice(ans3,true),item.createChoice(ans4,false)]);};
    if (ans4 == correctans){
item.setChoices([item.createChoice(ans1, false),item.createChoice(ans2,false),item.createChoice(ans3,false),item.createChoice(ans4,true)]);};
item.setPoints(1);
item.setRequired(true);
Anup M
  • 31
  • 4

1 Answers1

2

Store all the options in an array and shuffle the array.

  • Instead of storing each option in a different variable, create an array variable (options) and push all the possible options to this array.
  • Shuffle the resulting array (there are many ways to do this, but I used the one found in this answer -credits to Laurens Holst-).
  • Once the array is randomized, add each of these options to your item.

Code sample:

function addRandomizedOptions() {
  var sheet = SpreadsheetApp.getActiveSheet();
  var quest = sheet.getRange(1,4).getValue();
  var options = []
  options.push(sheet.getRange(1,4).getValue());
  options.push(sheet.getRange(1,5).getValue());
  options.push(sheet.getRange(1,6).getValue());
  options.push(sheet.getRange(1,9).getValue());
  shuffleArray(options);  
  var item = form.addMultipleChoiceItem();
  item.setChoices([
    item.createChoice(options[0], false),
    item.createChoice(options[1], false),
    item.createChoice(options[2], false),
    item.createChoice(options[3], true),    
  ]);
  item.setTitle(quest)
  item.setRequired(true);
  item.setPoints(1);
}

/* Randomize array in-place using Durstenfeld shuffle algorithm */
function shuffleArray(array) {
    for (let i = array.length - 1; i > 0; i--) {
        const j = Math.floor(Math.random() * (i + 1));
        [array[i], array[j]] = [array[j], array[i]];
    }
}

Note:

  • There's a fair amount of repetition in your code, including the recurrent calls to getValue() instead of using getValues() once, and using SpreadsheetApp.getActiveSheet() many times instead of storing the active sheet in a variable (fixed that in the code sample) as well as creating the choices one by one. I'd suggest you to try reworking that a bit in order to improve efficiency.

Related:

Iamblichus
  • 18,540
  • 2
  • 11
  • 27