Search in sources :

Example 6 with SelectOneData

use of org.javarosa.core.model.data.SelectOneData in project javarosa by opendatakit.

the class FormEntryPrompt method getAnswerText.

public String getAnswerText() {
    IAnswerData data = this.getAnswerValue();
    if (data == null)
        return null;
    else {
        String text;
        // and multi-selects.
        if (data instanceof SelectOneData) {
            text = this.getSelectItemText((Selection) data.getValue());
        } else if (data instanceof SelectMultiData) {
            StringBuilder b = new StringBuilder();
            List<Selection> values = (List<Selection>) data.getValue();
            for (Selection value : values) {
                b.append(this.getSelectItemText(value)).append(" ");
            }
            text = b.toString();
        } else {
            text = data.getDisplayText();
        }
        if (getControlType() == Constants.CONTROL_SECRET) {
            StringBuilder b = new StringBuilder();
            for (int i = 0; i < text.length(); ++i) {
                b.append("*");
            }
            text = b.toString();
        }
        return text;
    }
}
Also used : IAnswerData(org.javarosa.core.model.data.IAnswerData) SelectOneData(org.javarosa.core.model.data.SelectOneData) SelectMultiData(org.javarosa.core.model.data.SelectMultiData) Selection(org.javarosa.core.model.data.helper.Selection) ArrayList(java.util.ArrayList) List(java.util.List) ConstraintHint(org.javarosa.core.model.condition.pivot.ConstraintHint) Constraint(org.javarosa.core.model.condition.Constraint)

Example 7 with SelectOneData

use of org.javarosa.core.model.data.SelectOneData in project javarosa by opendatakit.

the class FormDef method attachControlsToInstanceData.

private void attachControlsToInstanceData(TreeElement node) {
    for (int i = 0; i < node.getNumChildren(); i++) {
        attachControlsToInstanceData(node.getChildAt(i));
    }
    IAnswerData val = node.getValue();
    List<Selection> selections = null;
    if (val instanceof SelectOneData) {
        selections = new ArrayList<Selection>();
        selections.add((Selection) val.getValue());
    } else if (val instanceof SelectMultiData) {
        selections = (List<Selection>) val.getValue();
    }
    if (selections != null) {
        QuestionDef q = findQuestionByRef(node.getRef(), this);
        if (q == null) {
            throw new RuntimeException("FormDef.attachControlsToInstanceData: can't find question to link");
        }
        if (q.getDynamicChoices() != null) {
        // droos: i think we should do something like initializing the
        // itemset here, so that default answers
        // can be linked to the selectchoices. however, there are
        // complications. for example, the itemset might
        // not be ready to be evaluated at form initialization; it may
        // require certain questions to be answered
        // first. e.g., if we evaluate an itemset and it has no choices, the
        // xform engine will throw an error
        // itemset TODO
        }
        for (Selection s : selections) {
            s.attachChoice(q);
        }
    }
}
Also used : IAnswerData(org.javarosa.core.model.data.IAnswerData) SelectOneData(org.javarosa.core.model.data.SelectOneData) SelectMultiData(org.javarosa.core.model.data.SelectMultiData) Selection(org.javarosa.core.model.data.helper.Selection) List(java.util.List) ArrayList(java.util.ArrayList) ExtWrapList(org.javarosa.core.util.externalizable.ExtWrapList) Constraint(org.javarosa.core.model.condition.Constraint)

Example 8 with SelectOneData

use of org.javarosa.core.model.data.SelectOneData in project collect by opendatakit.

the class ExternalAnswerResolver method resolveAnswer.

@Override
public IAnswerData resolveAnswer(String textVal, TreeElement treeElement, FormDef formDef) {
    QuestionDef questionDef = XFormParser.ghettoGetQuestionDef(treeElement.getDataType(), formDef, treeElement.getRef());
    if (questionDef != null && (questionDef.getControlType() == Constants.CONTROL_SELECT_ONE || questionDef.getControlType() == Constants.CONTROL_SELECT_MULTI)) {
        boolean containsSearchExpression = false;
        XPathFuncExpr xpathExpression = null;
        try {
            xpathExpression = ExternalDataUtil.getSearchXPathExpression(questionDef.getAppearanceAttr());
        } catch (Exception e) {
            Timber.e(e);
            // there is a search expression, but has syntax errors
            containsSearchExpression = true;
        }
        if (xpathExpression != null || containsSearchExpression) {
            // that means that we have dynamic selects
            // read the static choices from the options sheet
            List<SelectChoice> staticChoices = questionDef.getChoices();
            for (int index = 0; index < staticChoices.size(); index++) {
                SelectChoice selectChoice = staticChoices.get(index);
                String selectChoiceValue = selectChoice.getValue();
                if (ExternalDataUtil.isAnInteger(selectChoiceValue)) {
                    Selection selection = selectChoice.selection();
                    switch(questionDef.getControlType()) {
                        case Constants.CONTROL_SELECT_ONE:
                            {
                                if (selectChoiceValue.equals(textVal)) {
                                    // we just need to make sure, so we will override that.
                                    if (questionDef.getControlType() == Constants.CONTROL_SELECT_ONE) {
                                        // we don't need another, just return the static choice.
                                        return new SelectOneData(selection);
                                    }
                                }
                                break;
                            }
                        case Constants.CONTROL_SELECT_MULTI:
                            {
                                // we should search in a potential comma-separated string of
                                // values for a match
                                // copied from org.javarosa.xform.util.XFormAnswerDataParser
                                // .getSelections()
                                List<String> textValues = DateUtils.split(textVal, XFormAnswerDataSerializer.DELIMITER, true);
                                if (textValues.contains(textVal)) {
                                    // choice.
                                    if (selectChoiceValue.equals(textVal)) {
                                        // this means that the user selected ONLY the static
                                        // answer, so just return that
                                        List<Selection> customSelections = new ArrayList<Selection>();
                                        customSelections.add(selection);
                                        return new SelectMultiData(customSelections);
                                    } else {
                                    // we will ignore it for now since we will return that
                                    // selection together with the dynamic ones.
                                    }
                                }
                                break;
                            }
                        default:
                            {
                                // There is a bug if we get here, so let's throw an Exception
                                throw createBugRuntimeException(treeElement, textVal);
                            }
                    }
                } else {
                    switch(questionDef.getControlType()) {
                        case Constants.CONTROL_SELECT_ONE:
                            {
                                // the default implementation will search for the "textVal"
                                // (saved answer) inside the static choices.
                                // Since we know that there isn't such, we just wrap the textVal
                                // in a virtual choice in order to
                                // create a SelectOneData object to be used as the IAnswer to the
                                // TreeElement.
                                // (the caller of this function is searching for such an answer
                                // to populate the in-memory model.)
                                SelectChoice customSelectChoice = new SelectChoice(textVal, textVal, false);
                                customSelectChoice.setIndex(index);
                                return new SelectOneData(customSelectChoice.selection());
                            }
                        case Constants.CONTROL_SELECT_MULTI:
                            {
                                // we should create multiple selections and add them to the pile
                                List<SelectChoice> customSelectChoices = createCustomSelectChoices(textVal);
                                List<Selection> customSelections = new ArrayList<Selection>();
                                for (SelectChoice customSelectChoice : customSelectChoices) {
                                    customSelections.add(customSelectChoice.selection());
                                }
                                return new SelectMultiData(customSelections);
                            }
                        default:
                            {
                                // There is a bug if we get here, so let's throw an Exception
                                throw createBugRuntimeException(treeElement, textVal);
                            }
                    }
                }
            }
            // if we get there then that means that we have a bug
            throw createBugRuntimeException(treeElement, textVal);
        }
    }
    // default behavior matches original behavior (for static selects, etc.)
    return super.resolveAnswer(textVal, treeElement, formDef);
}
Also used : SelectOneData(org.javarosa.core.model.data.SelectOneData) SelectChoice(org.javarosa.core.model.SelectChoice) Selection(org.javarosa.core.model.data.helper.Selection) XPathFuncExpr(org.javarosa.xpath.expr.XPathFuncExpr) SelectMultiData(org.javarosa.core.model.data.SelectMultiData) ArrayList(java.util.ArrayList) List(java.util.List) QuestionDef(org.javarosa.core.model.QuestionDef)

Example 9 with SelectOneData

use of org.javarosa.core.model.data.SelectOneData in project collect by opendatakit.

the class GeneralSelectOneWidgetTest method getNextAnswer.

@NonNull
@Override
public SelectOneData getNextAnswer() {
    List<SelectChoice> selectChoices = getSelectChoices();
    int selectedIndex = Math.abs(random.nextInt()) % selectChoices.size();
    SelectChoice selectChoice = selectChoices.get(selectedIndex);
    Selection selection = new Selection(selectChoice);
    return new SelectOneData(selection);
}
Also used : SelectOneData(org.javarosa.core.model.data.SelectOneData) SelectChoice(org.javarosa.core.model.SelectChoice) Selection(org.javarosa.core.model.data.helper.Selection) NonNull(android.support.annotation.NonNull)

Example 10 with SelectOneData

use of org.javarosa.core.model.data.SelectOneData in project javarosa by opendatakit.

the class FormEntryPrompt method getAnswerValue.

// note: code overlap with FormDef.copyItemsetAnswer
public IAnswerData getAnswerValue() {
    QuestionDef q = getQuestion();
    ItemsetBinding itemset = q.getDynamicChoices();
    if (itemset != null) {
        if (itemset.valueRef != null) {
            List<SelectChoice> choices = getSelectChoices();
            List<String> preselectedValues = new ArrayList<String>();
            // determine which selections are already present in the answer
            if (itemset.copyMode) {
                TreeReference destRef = itemset.getDestRef().contextualize(mTreeElement.getRef());
                List<TreeReference> subNodes = form.getEvaluationContext().expandReference(destRef);
                for (int i = 0; i < subNodes.size(); i++) {
                    TreeElement node = form.getMainInstance().resolveReference(subNodes.get(i));
                    String value = itemset.getRelativeValue().evalReadable(form.getMainInstance(), new EvaluationContext(form.getEvaluationContext(), node.getRef()));
                    preselectedValues.add(value);
                }
            } else {
                List<Selection> sels;
                IAnswerData data = mTreeElement.getValue();
                if (data instanceof SelectMultiData) {
                    sels = (List<Selection>) data.getValue();
                } else if (data instanceof SelectOneData) {
                    sels = new ArrayList<Selection>(1);
                    sels.add((Selection) data.getValue());
                } else {
                    sels = new ArrayList<Selection>(0);
                }
                for (int i = 0; i < sels.size(); i++) {
                    preselectedValues.add(sels.get(i).xmlValue);
                }
            }
            // populate 'selection' with the corresponding choices (matching 'value') from the dynamic choiceset
            List<Selection> selection = new ArrayList<Selection>();
            for (int i = 0; i < preselectedValues.size(); i++) {
                String value = preselectedValues.get(i);
                SelectChoice choice = null;
                for (int j = 0; j < choices.size(); j++) {
                    SelectChoice ch = choices.get(j);
                    if (value.equals(ch.getValue())) {
                        choice = ch;
                        break;
                    }
                }
                // will no longer be an option this go around
                if (choice != null) {
                    selection.add(choice.selection());
                }
            }
            // convert to IAnswerData
            if (selection.size() == 0) {
                return null;
            } else if (q.getControlType() == Constants.CONTROL_SELECT_MULTI) {
                return new SelectMultiData(selection);
            } else if (q.getControlType() == Constants.CONTROL_SELECT_ONE) {
                // do something if more than one selected?
                return new SelectOneData(selection.get(0));
            } else {
                throw new RuntimeException("can't happen");
            }
        } else {
            // cannot map up selections without <value>
            return null;
        }
    } else {
        // static choices
        return mTreeElement.getValue();
    }
}
Also used : IAnswerData(org.javarosa.core.model.data.IAnswerData) SelectOneData(org.javarosa.core.model.data.SelectOneData) SelectChoice(org.javarosa.core.model.SelectChoice) Selection(org.javarosa.core.model.data.helper.Selection) ArrayList(java.util.ArrayList) ItemsetBinding(org.javarosa.core.model.ItemsetBinding) ConstraintHint(org.javarosa.core.model.condition.pivot.ConstraintHint) Constraint(org.javarosa.core.model.condition.Constraint) TreeElement(org.javarosa.core.model.instance.TreeElement) SelectMultiData(org.javarosa.core.model.data.SelectMultiData) TreeReference(org.javarosa.core.model.instance.TreeReference) EvaluationContext(org.javarosa.core.model.condition.EvaluationContext) QuestionDef(org.javarosa.core.model.QuestionDef)

Aggregations

SelectOneData (org.javarosa.core.model.data.SelectOneData)14 SelectMultiData (org.javarosa.core.model.data.SelectMultiData)8 Selection (org.javarosa.core.model.data.helper.Selection)8 ArrayList (java.util.ArrayList)5 Constraint (org.javarosa.core.model.condition.Constraint)5 SelectChoice (org.javarosa.core.model.SelectChoice)4 IAnswerData (org.javarosa.core.model.data.IAnswerData)4 List (java.util.List)3 Date (java.util.Date)2 QuestionDef (org.javarosa.core.model.QuestionDef)2 EvaluationContext (org.javarosa.core.model.condition.EvaluationContext)2 ConstraintHint (org.javarosa.core.model.condition.pivot.ConstraintHint)2 BooleanData (org.javarosa.core.model.data.BooleanData)2 DateData (org.javarosa.core.model.data.DateData)2 DateTimeData (org.javarosa.core.model.data.DateTimeData)2 DecimalData (org.javarosa.core.model.data.DecimalData)2 GeoPointData (org.javarosa.core.model.data.GeoPointData)2 GeoShapeData (org.javarosa.core.model.data.GeoShapeData)2 GeoTraceData (org.javarosa.core.model.data.GeoTraceData)2 IntegerData (org.javarosa.core.model.data.IntegerData)2