Nested callbacks and test.selected conditions problem

PennController for IBEX Forums Support Nested callbacks and test.selected conditions problem

This topic contains 2 replies, has 2 voices, and was last updated by Avatar mrhelfrich 1 month, 1 week ago.

Viewing 3 posts - 1 through 3 (of 3 total)
  • Author
    Posts
  • #7058
    Avatar
    mrhelfrich
    Participant

    Hello, not sure how to describe this problem succinctly so my topic title is a little vague. I am trying to nest multiple test commands for dropdowns such that when one dropdown is selected, based on their selection, a second dropdown may appear. Explaining the reasoning is a little more complicated so I’ll first post the code with my basic issue:

    newTrial("WIPtrial",
        newText("DD1Text","Yes goes to 2nd DropDown, No will lock the user out of participating (not implemented yet)"),
        newDropDown("DD1Drop","Please select a response").add("Yes","No"),
        newText("DD2Text","Many choices DropDown"),
        getText("DD1Text").print(),
        getDropDown("DD1Drop").print()
            .callback(
                getDropDown("DD1Drop")
                    .test.selected("Yes").success(
                        getButton("ContinueNo").remove(),
                        getText("DD2Text").print(), //line "X" for simplicity //For some reason, this line runs but the line below isn't run directly afterward, the next executed line is the Error text
                        newDropDown("DD2Drop","Please select a response").print().add( //line "Y" for simplicity //using getDropDown doesn't solve the problem either.
                            "Option1","Option2","Option3","Option4","Option5","Option6")
                            .callback(
                                getDropDown("DD2Drop")
                                    .test.selected().success(newButton("ContinueYes","[Clicking this should end trial]").print())
                                )
                        )
                    .test.selected("No").success(
                        getButton("ContinueYes").remove(),
                        getText("DD2Text").remove(),
                        getDropDown("DD2Drop").remove(),
                        newButton("ContinueNo","[Clicking this will lock user out of participating and provide explanation (not implemented)]").print()
                        )                    
                ).wait(), //putting .wait() here makes the first DropDown required before progressing but not the 2nd dropdown, so it only delays the problem
    
        newText("Error: Trial would have ended").print().wait() //Debug statement, not meant to be part of the final script, just keeps the trial from ending automatically
    )

    When the code above runs, it will wait for the first dropdown to be responded to before continuing, and if Yes is selected, it does proceed to print the next line (called “X” in a comment for simplicity). After printing line X, it prints the text “Error: Trial would have ended” which should only be printed when the trial is set to otherwise end, and then it prints the second dropdown (line “Y”). The log in the debugger tells me that line X executes after “Yes” is selected, and then the next thing executed is the print command for the Error: text.

    I’ve tried many combinations of adding .wait() to different places to try and get the program to print the second dropdown and wait for a response but nothing works since I believe it is running the line for the 2nd dropdown after the trial is otherwise set to end. If I could get the script to complete all of the commands indented more than once first before reaching the end of the trial I think I could make everything else work on my own.

    Extra information/clarification that may not be needed:
    My normal way of solving this would be to add a continue button that the program waits on and only becomes visible/clickable after all of the dropdowns are complete (since the second dropdown does function, it appears after the trial would otherwise have ended), but my plan here is to have two different outcomes for this one trial. If the participant picks Yes to DropDown1, they get a follow-up question, and upon answering that follow-up, they proceed to the next trial in the sequence (not included in here for space), but if they select “No” to DropDown1, they will be instead taken to an explanation that they aren’t eligible to participate and there will not be any way to progress further. The yes/no question will be an eligibility question in the actual study and we need to exclude participants that reply No. Using a single button to end the trial wouldn’t work as the trial should only end (and therefore advance along the sequence) if Yes was selected.

    Thanks for any assistance you can offer,
    Max

    #7060
    Jeremy
    Jeremy
    Keymaster

    Hi,

    How about this?

    newTrial("WIPtrial",
        newButton("ContinueYes","[Clicking this should end trial]"),
        newButton("ContinueNo","[Clicking this will lock user out of participating and provide explanation]")
            .callback(
                clear(),
                newText("Explanation goes here").print()
            )
        ,
        newDropDown("DD2Drop","Please select a response")
            .add("Option1","Option2","Option3","Option4","Option5","Option6")
            .callback( getButton("ContinueYes").print() )
        ,
        newText("DD1Text","Yes goes to 2nd DropDown, No will lock the user out of participating (not implemented yet)")
            .print()
        ,
        newDropDown("DD1Drop","Please select a response")
            .add("Yes","No")
            .callback( self.test.selected("Yes")
                .success(
                    getButton("ContinueNo").remove(),
                    newText("DD2Text","Many choices DropDown").print(),
                    getDropDown("DD2Drop").print()
                )
                .failure(
                    getButton("ContinueYes").remove(),
                    getText("DD2Text").remove(),
                    getDropDown("DD2Drop").remove(),
                    getButton("ContinueNo").print()
                )
            )
            .print()
            .wait()
        ,
        getButton("ContinueYes").wait() // this can only complete when button is printed
    )
    

    Jeremy

    #7063
    Avatar
    mrhelfrich
    Participant

    Thank you very much, that solves the problem and is also much easier to understand than what I had written!

Viewing 3 posts - 1 through 3 (of 3 total)

You must be logged in to reply to this topic.