Welcome to the LimeSurvey Community Forum

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

JavaScript conversion of answer to numeric value

  • BG2013
  • BG2013's Avatar Topic Author
  • Offline
  • New Member
  • New Member
More
7 years 4 months ago #143513 by BG2013
Hello,
I am building several generic matrixes for prioritizing respondent opinions, and am looking for a way to capture the answer from a previous slider subquestion in JavaScript.

Non-zero answers from the preceding slider question are numeric, but importing the answer into JavaScript results in a non-numeric variable that cannot be used in computation.

Example .lss file attached. The script embedded in the equation-type question is greatly simplified for test purposes. The one line commented out is the code I have been using to fetch the answer from the previous subquestion. I am aware that the quotes make it a string; instead, I would like to import or convert it into the script as a numeric value.

While I have demonstrated to myself that the task can be done solely with Expression Manager syntax, the resulting EM code is too complex to modify, replicate, and manage for the several sizes of matrixes and dozens of question combinations needed in the survey.

After searching the LS forum and manual, as well as JS built-in objects, I’ve been unable to find a means to retain the numeric character of the previous question answer. My experience with LS and JS is not extensive, so forgive me if I am missing some simple solution.

Using LS 2.54.5+161019-on-xampp-win32, on Win 10 PC.

Thank you.
The topic has been locked.
  • tpartner
  • tpartner's Avatar
  • Offline
  • LimeSurvey Community Team
  • LimeSurvey Community Team
More
7 years 4 months ago - 7 years 4 months ago #143523 by tpartner
I see a couple of problems:
- Everything is on a single page so when the page loads and your script fires, there is no value for the slider
- Expression Manager piped values are wrapped in a <span> element so you'll need to clean that up (that's why you are seeing NAN)

Also note that you cannot use JavaScript to write data to equation type questions so your inserted text will be for display purposes only.

I would do this:
1) Insert an expression into the equation question to get the slider value - {singleQ_SQ001}
2) Hide the associated <span> element with JavaScript
3) Put a listener on the slider to run your calculations and insert your text as it is moved

Code:
<script type="text/javascript" charset="utf-8">
 
  $(document).ready(function() {  
 
    // Identify this question
    var thisQuestion = $('#question{QID}');
 
    // Hide the equation question value
    $('.question-text span[id^="LEMtailor_Q_"]:eq(0)', thisQuestion).hide();
 
    // Listener on the slider
    $('.numeric-multi:eq(0) input[type=text]:eq(0)').on('slideStop', function(event) {
      var ansSQ001 = $.trim($('.question-text span[id^="LEMtailor_Q_"]:eq(0)', thisQuestion).text()); // get subquestion answer
      var ans = ansSQ001;
      var A1 = 1; // matrix cell A1
      var B1 = 2; // matrix cell B1
      if (ans<0) { B1 = 1/Math.abs(ans); }
      else { B1 = ans; } // 'inverts' negative scores
      var A2 = 1/B1; // matrix cell A2
      var B2 = 1; // matrix cell B2
      var ColA = A1 + A2; // matrix column A
      var ColB = B1 + B2; // matrix column B
      var Row1norm = (A1/ColA + B1/ColB)/2; // average of normalized cells A1 and B1
      var Row2norm = (A2/ColA + B2/ColB)/2; // average of normalized cells A2 and B2
      var Row1avg = Row1norm.toFixed(2); // Row 1 average rounded to 2 decimal places
      var Row2avg = Row2norm.toFixed(2); // Row 2 average rounded to 2 decimal places
      // Clear old text
      $('.question-text .inserted-text', thisQuestion).remove();
      // Insert new text
      $('.question-text', thisQuestion).append('<div class="inserted-text">\
                              2x2 matrix, comparing Alpa to Beta\
                              <br><br>'+ans+'\
                              <br>priority Alpha: '+Row1avg+'\
                              <br>priority Beta: '+Row2avg+'\
                            </div>');
    });  
  });
</script>

Sample survey attached:

File Attachment:

File Name: limesurvey...6464.lss
File Size:16 KB

Cheers,
Tony Partner

Solutions, code and workarounds presented in these forums are given without any warranty, implied or otherwise.
Last edit: 7 years 4 months ago by tpartner.
The following user(s) said Thank You: BG2013
The topic has been locked.
  • BG2013
  • BG2013's Avatar Topic Author
  • Offline
  • New Member
  • New Member
More
7 years 4 months ago #143594 by BG2013
tpartner,

You are indeed generous with your contributions to this community.

The sample code works very well. (However, the positive subquestion values were leading to computational errors. Once I forced variable ans in the phrase [else { B1 = ans; }] to a number using a unary plus (+) operator, the errors went away. The matrix still evaluates to NaN for a subquestion value of zero, but I intend to include a validation sequence for the slider that prohibits a zero value.)

I had not considered invoking LEM developer functions. Also, thank you very much for the insight on limitations of using JS to write data in Equation-type questions.

Two follow-on questions, if I may:

1. Depending on options selected by the respondent, the respondent will answer 1, 3, or 6 slider subquestions, requiring computation of a 2x2, 3x3, or 4x4 matrix, respectively. How can this technique of invoking #question{QID} for thisQuestion be expanded to process 6 subquestions concurrently? I’m thinking of concatenating the 1, 3, or 6 slider subquestion answers into a single EM-format string, and then using JS to parse the variables out as needed for the cells in the correspondingly-sized matrix. Is there a better way?

2. Depending on the matrix size, the computations will result in 2, 3, or 4 priority values (for combinations of Alpha, Beta, Gamma, and Delta). I would like to populate the database with the multiple priority values and their associated labels. If the result was a single value, the question answer could be stored as a single accessible field. How can JS or EM be used to store multiple results of the Equation question computation as “previous fields” that can be queried later?

Thank you again,
BG2013
The topic has been locked.
  • tpartner
  • tpartner's Avatar
  • Offline
  • LimeSurvey Community Team
  • LimeSurvey Community Team
More
7 years 4 months ago - 7 years 4 months ago #143598 by tpartner
Well, you kind of lost me with where you're going :) but...

1) Maybe several equations questions placed one after the other.
Code:
    ...
    var thisQuestion = $('#question{QID}');
    var equation2= $(thisQuestion).nextAll('.equation:eq(1)');
    var equation3= $(thisQuestion).nextAll('.equation:eq(2)');
    var equation4= $(thisQuestion).nextAll('.equation:eq(3)');
    ...
 
    ...
      var ansSQ001 = $.trim($('.question-text span[id^="LEMtailor_Q_"]:eq(0)', thisQuestion).text());
      var ansSQ002 = $.trim($('.question-text span[id^="LEMtailor_Q_"]:eq(0)', equation2).text());
      var ansSQ003 = $.trim($('.question-text span[id^="LEMtailor_Q_"]:eq(0)', equation3).text());
      var ansSQ004 = $.trim($('.question-text span[id^="LEMtailor_Q_"]:eq(0)', equation4).text());
    ...

2) Use JavaScript to write the values to hidden short-text questions.

Cheers,
Tony Partner

Solutions, code and workarounds presented in these forums are given without any warranty, implied or otherwise.
Last edit: 7 years 4 months ago by tpartner.
The following user(s) said Thank You: BG2013
The topic has been locked.
  • BG2013
  • BG2013's Avatar Topic Author
  • Offline
  • New Member
  • New Member
More
7 years 4 months ago #143600 by BG2013
tpartner,

Thanks again. I'll give your approaches a try and post my outcome.

Regards,
BG2013
The topic has been locked.
  • BG2013
  • BG2013's Avatar Topic Author
  • Offline
  • New Member
  • New Member
More
7 years 4 months ago #144118 by BG2013
tpartner,

Thank you for your assistance. Using your guidance to pull several elements from the preceding questions and a switch statement that accounts for the 50 different combinations of respondent choices, the solution is finally working.

Regards,
BG2013
The topic has been locked.

Lime-years ahead

Online-surveys for every purse and purpose