Cart Buy Licenses Contact Support Login/Register
v 1.8.6
v 1.8.6
Overview Examples Docs Source Download

Async function in Expression

Edit in CodeSandbox
import Vue from "vue"; import * as Survey from "survey-vue"; import "survey-vue/survey.css"; import "./index.css"; Survey.StylesManager.applyTheme("orange"); //Hashtable for countries information var countriesInformation = {}; //The list of listeners var isReadyCallbackList = []; function setValueAndnotifyListeners(country, res) { countriesInformation[country] = res; for(var i = 0; i < isReadyCallbackList.length; i ++) { isReadyCallbackList[i](res); } isReadyCallbackList = []; } function getCountryInfoAjax(survey, country, isReadyCallback) { if (!country) { isReadyCallback({ isFound: false }); return null; } country = country.toLowerCase(); var countryInfo = countriesInformation[country]; if(!!countryInfo && (countryInfo.status == "processing")) { isReadyCallbackList.push(isReadyCallback); return null; } if(!!countryInfo && countryInfo.status == "completed") { isReadyCallback(countryInfo); return countryInfo; } countriesInformation[country] = {status: "processing"}; isReadyCallbackList.push(isReadyCallback); survey.setVariable("country_request_processing", true); $.ajax({ url: "https://restcountries.eu/rest/v2/name/" + country, type: "GET", success: function (data) { survey.setVariable("country_request_processing", false); if (!data || data.length < 1) { setValueAndnotifyListeners(country, {status: "completed", isFound: false}); return; } var countryValue = data[0]; var currencyValue = countryValue.currencies.length > 0 ? countryValue.currencies[0] : {}; setValueAndnotifyListeners(country, {status: "completed", isFound: true, capital: countryValue.capital, currency: JSON.stringify(currencyValue)}); }, error: function (xhr, ajaxOptions, thrownError) { survey.setVariable("country_request_processing", false); setValueAndnotifyListeners(country, {status: "completed", isFound: false}); } }); return null; } function getCountryInfo(context, params, property) { if(params.length < 1) { context.returnResult(null); } var self = this; var isReady = function(countryInfo) { context.returnResult(countryInfo[property]); } return getCountryInfoAjax(context.survey, params[0], isReady); } function getCountryCapital(params) { return getCountryInfo(this, params, "capital"); } function getCountryCurrency(params) { return getCountryInfo(this, params, "currency"); } function isCountryExist(params) { return getCountryInfo(this, params, "isFound"); } Survey.FunctionFactory.Instance.register("getCountryCapital", getCountryCapital, true); Survey.FunctionFactory.Instance.register("getCountryCurrency", getCountryCurrency, true); Survey.FunctionFactory.Instance.register("isCountryExist", isCountryExist, true); var json = { checkErrorsMode: "onValueChanged", elements: [ { type: "html", name: "requesting", html: "The data is requesting", visibleIf: "{country_request_processing} = true" }, { type: "text", name: "country", title: "Please enter the country:", validators: [ { type: "expression", expression: "isCountryExist({country}) = true", text: "We could not find country with this name." } ] }, { type: "expression", name: "capital", title: "Capital of {country} is:", expression: "getCountryCapital({country})", visibleIf: "{capital} notempty" }, { type: "expression", name: "currency", title: "Currency in {country} is:", expression: "getCountryCurrency({country})", visibleIf: "{currency} notempty" } ] }; let survey = new Survey.Model(json); survey.onComplete.add(function(result) { document.querySelector('#surveyResult').textContent = "Result JSON:\n" + JSON.stringify(result.data, null, 3); }); var app = new Vue({ el: '#surveyElement', data: { survey: survey } }); <div id="surveyElement" style="display:inline-block;width:100%;"> <survey :survey='survey' /> </div> <div id="surveyResult"></div>

Calculate expression using asynchron functions - Expression question


                        
        
            Survey.StylesManager.applyTheme("orange");
        

//Hashtable for countries information
var countriesInformation = {};
//The list of listeners
var isReadyCallbackList = [];
function setValueAndnotifyListeners(country, res) {
    countriesInformation[country] = res;
    for(var i = 0; i < isReadyCallbackList.length; i ++) {
        isReadyCallbackList[i](res);
    }
    isReadyCallbackList = [];
}
function getCountryInfoAjax(survey, country, isReadyCallback) {
    if (!country) {
        isReadyCallback({ isFound: false });
        return null;
    }
    country = country.toLowerCase();
    var countryInfo = countriesInformation[country];
    if(!!countryInfo && (countryInfo.status == "processing")) {
        isReadyCallbackList.push(isReadyCallback);
        return null;
    }
    if(!!countryInfo  && countryInfo.status == "completed") {
        isReadyCallback(countryInfo);
        return countryInfo;
    }
    countriesInformation[country] = {status: "processing"};
    isReadyCallbackList.push(isReadyCallback);

    survey.setVariable("country_request_processing", true);
    $.ajax({
        url: "https://restcountries.eu/rest/v2/name/" + country,
        type: "GET",
        success: function (data) {
            survey.setVariable("country_request_processing", false);
            if (!data || data.length < 1) {
                setValueAndnotifyListeners(country, {status: "completed", isFound: false});
                return;
            }
            var countryValue = data[0];
            var currencyValue = countryValue.currencies.length > 0 ? countryValue.currencies[0] : {};
            setValueAndnotifyListeners(country, {status: "completed", isFound: true, capital: countryValue.capital, currency: JSON.stringify(currencyValue)});
        },
        error: function (xhr, ajaxOptions, thrownError) {
            survey.setVariable("country_request_processing", false);
            setValueAndnotifyListeners(country, {status: "completed", isFound: false});
        }
    });
    return null;
}
function getCountryInfo(context, params, property) {
    if(params.length < 1) {
        context.returnResult(null);
    }
    var self = this;
    var isReady = function(countryInfo) {
        context.returnResult(countryInfo[property]);
    }
    return getCountryInfoAjax(context.survey, params[0], isReady);
}
function getCountryCapital(params) {
    return getCountryInfo(this, params, "capital");
}
function getCountryCurrency(params) {
    return getCountryInfo(this, params, "currency");
}
function isCountryExist(params) {
    return getCountryInfo(this, params, "isFound");
}

Survey.FunctionFactory.Instance.register("getCountryCapital", getCountryCapital, true);
Survey.FunctionFactory.Instance.register("getCountryCurrency", getCountryCurrency, true);
Survey.FunctionFactory.Instance.register("isCountryExist", isCountryExist, true);
            
                var json = {
  checkErrorsMode: "onValueChanged",
  elements: [
    {
      type: "html",
      name: "requesting",
      html: "The data is requesting",
      visibleIf: "{country_request_processing} = true"
    },
    {
      type: "text",
      name: "country",
      title: "Please enter the country:",
      validators: [
        {
          type: "expression",
          expression: "isCountryExist({country}) = true",
          text: "We could not find country with this name."
        }
      ]
    },
    {
      type: "expression",
      name: "capital",
      title: "Capital of {country} is:",
      expression: "getCountryCapital({country})",
      visibleIf: "{capital} notempty"
    },
    {
      type: "expression",
      name: "currency",
      title: "Currency in {country} is:",
      expression: "getCountryCurrency({country})",
      visibleIf: "{currency} notempty"
    }
  ]
};

                window.survey = new Survey.Model(json);
            
        
            survey.onComplete.add(function(result) {
            document.querySelector('#surveyResult').textContent =
            "Result JSON:\n" + JSON.stringify(result.data, null, 3);
            });
        
        
            var app = new Vue({
            el: '#surveyElement',
            data:
            {
            survey: survey
            }
            });
        

                    
<!DOCTYPE html>
<html lang="en">
<head>
    <title>Calculate expression using asynchron functions - Expression question, Vue Survey Library Example</title>

<meta name="viewport" content="width=device-width" />
    <script src="https://unpkg.com/jquery"></script>
    <script src="https://unpkg.com/vue/dist/vue.js"></script>
<script src="https://surveyjs.azureedge.net/1.8.6/survey.vue.js"></script>
<link href="https://surveyjs.azureedge.net/1.8.6/survey.css" type="text/css" rel="stylesheet" />
    <link rel="stylesheet" href="./index.css">

</head>
<body>
    
            <div id="surveyElement" style="display:inline-block;width:100%;">
                <survey :survey='survey' />
            </div>
    <div id="surveyResult"></div>

<script type="text/javascript" src="./index.js"></script>

</body>
</html>