collect
collect copied to clipboard
Field list does not update correctly
We've found a case where field lists do not update correctly when a question is answered. I'll format this issue in a way that allows us to add any other cases we might find down the line (before making fixes) here as well.
Trigger + Calculate + Relevant
Form
<?xml version="1.0"?>
<h:html xmlns="http://www.w3.org/2002/xforms" xmlns:ev="http://www.w3.org/2001/xml-events"
xmlns:h="http://www.w3.org/1999/xhtml" xmlns:jr="http://openrosa.org/javarosa"
xmlns:odk="http://www.opendatakit.org/xforms" xmlns:orx="http://openrosa.org/xforms"
xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<h:head>
<h:title>Trigger relevant</h:title>
<model odk:xforms-version="1.0.0">
<instance>
<data id="trigger" version="1">
<field-list>
<a/>
<b/>
</field-list>
<meta>
<instanceID/>
</meta>
</data>
</instance>
<bind nodeset="/data/field-list/a" type="string"/>
<bind nodeset="/data/field-list/b" relevant="selected( /data/field-list/a , 'show')" type="string"/>
<bind jr:preload="uid" nodeset="/data/meta/instanceID" readonly="true()" type="string"/>
</model>
</h:head>
<h:body>
<group appearance="field-list" ref="/data/field-list">
<label>Field List</label>
<select1 ref="/data/field-list/a">
<label>A</label>
<item>
<label>Show B</label>
<value>show</value>
</item>
<item>
<label>Hide B</label>
<value>hide</value>
</item>
<setvalue event="xforms-value-changed" ref="/data/field-list/b" value=" /data/field-list/a "/>
</select1>
<select1 ref="/data/field-list/b">
<label>B</label>
<item>
<label>Show B</label>
<value>show</value>
</item>
<item>
<label>Hide B</label>
<value>hide</value>
</item>
<setvalue event="xforms-value-changed" ref="/data/field-list/a" value=" /data/field-list/b "/>
</select1>
</group>
</h:body>
</h:html>
Test
rule.startAtMainMenu()
.copyForm("trigger-relevant.xml")
.startBlankForm("Trigger relevant")
.assertQuestion("A")
.assertTextDoesNotExist("B")
.clickOnText("Show B")
.assertQuestion("A")
.assertQuestion("B")
.clickOnText("Hide B", 1) // Click the second "Hide B"
.assertQuestion("A")
.assertTextDoesNotExist("B")
Notes
It would be good to take the opportunity to revise how widget values are saved as part of fixing this issue. We've chatted in the past about having widgets and onActivityResult
call a modified FormEntryViewModel#answerQuestion
that in turns calls FormController#answerQuestion
(or similar) and then some kind of optimized reload (probably through an interface) instead of using QuestionWidget#setData
, WaitingForDataRegistry
, WidgetValueChangedListener
etc.