I actually just spent a really long time figuring out answers to this question by piecing it together from the spotty documentation and a lot of web console inspection. Since by far the most useful information came from Stack Overflow, I wanted to put this question, and its answer, here for the future benefit of anyone else searching.
The question is, how can you add javascript to a question that will immediately save that question's answer into an embedded data field? Immediately, as in, not waiting until the next Qualtrics.SurveyEngine.AddOnLoad(). This involves the sub-question of how can you add javascript to a survey question and have it run when the Next button is clicked? And the sub-question of, how can you save embedded data fields that are dynamically named based on the question ID?
Caveat Emptor: all this javascript hacking is not explicitly supported by Qualtrics, so the code here may stop working eventually.
Here is how to get the response value of a slider and save it in an embedded data field with a name that is numbered based on the question ID. This way only works if the text input box for the slider is visible. There's probably a way to do it without that, too, maybe someone else can add that to the answers.
Qualtrics.SurveyEngine.addOnload(function()
{
// everything here runs when the page is loaded. So, we can get the Question ID here,
// but we can't get the response value until later.
var currentQuestionID = this.getQuestionInfo().QuestionID
//var resultEmbeddedName = currentQuestionID + "_result" //e.g. QID6_result
var resultEmbeddedName = "result_" + currentQuestionID.substring(3) //e.g. result_6
$('NextButton').onclick = function (event) {
// everything in here will run when you click the next button
// note that it has access to javascript variables from the enclosing function
// however, if you declare something in here with "var" then it will be a LOCAL variable
// the following alert will appear when you click the next button. For me, it appears twice;
// I'm not sure why.
// Save the current question's response value
var responseTextField = document.getElementById(currentQuestionID + '~1~result')
var currentResponse = responseTextField.value
alert("Result: " + currentResponse + "\nwill be available to future questions as: \n$" + "{e://Field/" + resultEmbeddedName + "}")
Qualtrics.SurveyEngine.setEmbeddedData(resultEmbeddedName, currentResponse)
// and now run the event that the normal next button is supposed to do
Qualtrics.SurveyEngine.navClick(event, 'NextButton')
}
});
For multiple choice items, it's a bit more complicated. Here's the code that works, with lots of comments and demos. Note that the variable "currentResponse" ends up holding the NUMBER of the chosen choice, while "currentChoiceText" ends up holding the text label for that choice (e.g. Yes or No.) So you can save whichever one you prefer.
Qualtrics.SurveyEngine.addOnload(function()
{
// everything here runs when the page is loaded. So, we can get the Question ID here,
// but we can't get the response value until later.
var currentQuestionID = this.getQuestionInfo().QuestionID
console.log("Current Question ID is: " + currentQuestionID)
//var resultEmbeddedName = currentQuestionID + "_result" //e.g. QID6_result
var resultEmbeddedName = "result_" + currentQuestionID.substring(3) //e.g. result_6
$('NextButton').onclick = function (event) {
// everything in here will run when you click the next button
// note that it has access to javascript variables from the enclosing function
// however, if you declare something in here with "var" then it will be a LOCAL variable
// the following alerts will appear when you click the next button. For me, it appears twice;
// I'm not sure why.
// Save the current question's response value
var questionObject = Qualtrics.SurveyEngine.getInstance(currentQuestionID)
var currentResponse = questionObject.getSelectedChoices()[0] //in case more than one is selected, it will only work here to take one!
var theQuestionInfo=questionObject.getQuestionInfo()
var choicesObject=theQuestionInfo.Choices
var thisChoiceObject=choicesObject[currentResponse]
var currentChoiceText=thisChoiceObject.Text
console.log("Number of the current choice is " + currentResponse)
console.log("Text of the current choice is " + currentChoiceText)
alert("Result: " + currentChoiceText + "\nwill be available to future questions as: \n$" + "{e://Field/" + resultEmbeddedName + "}")
Qualtrics.SurveyEngine.setEmbeddedData(resultEmbeddedName, currentChoiceText)
// and now run the event that the normal next button is supposed to do
Qualtrics.SurveyEngine.navClick(event, 'NextButton')
}
});
Both of these refer to the question ID dynamically, so they will work individually if you copy the question to a new one. Without needing to change any of the javascript code.
To test these, make a slider question or a multiple choice question and add the respective javascript. Then, make another slide after a page break (the page break is necessary to cause the appearance of the Next button). In that slide, put a piped text field like ${e://Field/result_1} or whatever the alert dialog tells you the saved value will be. When you preview the survey, you should see the value that was entered on the first question, in the piped text field of the second question.
As far as this demo goes, you could certainly achieve the same effect with just piped text. But if you have some reason that you want a question to actually immediately save its response into embedded data, this will do that for you.
Also, if you need to know how to run code when the Next button is clicked, this can be adapted for any general need for that.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With