From 822a571c90a2c8f1df603ede044587db91d99f46 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jorge=20Sa=CC=81nchez?= Date: Wed, 1 Jul 2020 07:23:10 +0200 Subject: [PATCH 01/11] Modify edit text control to show color by data element legend --- app/src/main/assets/paperwork.json | 2 +- .../forms/dataentry/EnrollmentRepository.kt | 3 +- .../fields/FieldViewModelFactory.java | 3 +- .../fields/FieldViewModelFactoryImpl.java | 7 ++-- .../fields/edittext/EditTextCustomHolder.java | 5 +++ .../fields/edittext/EditTextViewModel.java | 27 ++++++++++---- .../EventCaptureRepositoryImpl.java | 37 +++++++++++++++++-- .../EventSummaryRepositoryImpl.java | 2 +- .../adapters/FormAdapter.java | 4 +- .../utils/customviews/CustomTextView.java | 6 +++ .../enrollment/EnrollmentPresenterImplTest.kt | 3 ++ .../dhis2/utils/RulesUtilsProviderImplTest.kt | 3 +- 12 files changed, 82 insertions(+), 20 deletions(-) diff --git a/app/src/main/assets/paperwork.json b/app/src/main/assets/paperwork.json index 824a6e1243..52580831c3 100644 --- a/app/src/main/assets/paperwork.json +++ b/app/src/main/assets/paperwork.json @@ -1 +1 @@ -{"buildTime":"2020-06-26 09:19","gitSha":"ae5b01eaf"} \ No newline at end of file +{"buildTime":"2020-07-01 07:11","gitSha":"ae505e6d5"} \ No newline at end of file diff --git a/app/src/main/java/org/dhis2/data/forms/dataentry/EnrollmentRepository.kt b/app/src/main/java/org/dhis2/data/forms/dataentry/EnrollmentRepository.kt index be1f61c0d3..2333c6264f 100644 --- a/app/src/main/java/org/dhis2/data/forms/dataentry/EnrollmentRepository.kt +++ b/app/src/main/java/org/dhis2/data/forms/dataentry/EnrollmentRepository.kt @@ -204,7 +204,8 @@ class EnrollmentRepository( programTrackedEntityAttribute.renderType()?.mobile(), optionCount, attribute.style(), - attribute.fieldMask() + attribute.fieldMask(), + null ) return if (warning != null) { diff --git a/app/src/main/java/org/dhis2/data/forms/dataentry/fields/FieldViewModelFactory.java b/app/src/main/java/org/dhis2/data/forms/dataentry/fields/FieldViewModelFactory.java index abc649e775..688d1211eb 100644 --- a/app/src/main/java/org/dhis2/data/forms/dataentry/fields/FieldViewModelFactory.java +++ b/app/src/main/java/org/dhis2/data/forms/dataentry/fields/FieldViewModelFactory.java @@ -25,5 +25,6 @@ FieldViewModel create(@NonNull String id, @Nullable ValueTypeDeviceRendering fieldRendering, @Nullable Integer optionCount, @NonNull ObjectStyle objectStyle, - @Nullable String fieldMask); + @Nullable String fieldMask, + @Nullable String colorByLegend); } diff --git a/app/src/main/java/org/dhis2/data/forms/dataentry/fields/FieldViewModelFactoryImpl.java b/app/src/main/java/org/dhis2/data/forms/dataentry/fields/FieldViewModelFactoryImpl.java index 4e12ea552a..2d205ee16b 100644 --- a/app/src/main/java/org/dhis2/data/forms/dataentry/fields/FieldViewModelFactoryImpl.java +++ b/app/src/main/java/org/dhis2/data/forms/dataentry/fields/FieldViewModelFactoryImpl.java @@ -54,7 +54,8 @@ public FieldViewModelFactoryImpl(Map valueTypeHintMap) { public FieldViewModel create(@NonNull String id, @NonNull String label, @NonNull ValueType type, @NonNull Boolean mandatory, @Nullable String optionSet, @Nullable String value, @Nullable String section, @Nullable Boolean allowFutureDates, @NonNull Boolean editable, @Nullable ProgramStageSectionRenderingType renderingType, - @Nullable String description, @Nullable ValueTypeDeviceRendering fieldRendering, @Nullable Integer optionCount, ObjectStyle objectStyle, @Nullable String fieldMask) { + @Nullable String description, @Nullable ValueTypeDeviceRendering fieldRendering, @Nullable Integer optionCount, ObjectStyle objectStyle, @Nullable String fieldMask, + @Nullable String colorByLegend) { isNull(type, "type must be supplied"); if (!isEmpty(optionSet)) { @@ -89,7 +90,7 @@ public FieldViewModel create(@NonNull String id, @NonNull String label, @NonNull if (fieldRendering != null && (fieldRendering.type().equals(ValueTypeRenderingType.QR_CODE) || fieldRendering.type().equals(ValueTypeRenderingType.BAR_CODE))) { return ScanTextViewModel.create(id, label, mandatory, value, section, editable, optionSet, description, objectStyle, fieldRendering); } else { - return EditTextViewModel.create(id, label, mandatory, value, valueTypeHintMap.get(type), 1, type, section, editable, description, fieldRendering, objectStyle, fieldMask); + return EditTextViewModel.create(id, label, mandatory, value, valueTypeHintMap.get(type), 1, type, section, editable, description, fieldRendering, objectStyle, fieldMask, colorByLegend); } case IMAGE: return PictureViewModel.create(id, label, mandatory, value, section, editable, description, objectStyle); @@ -110,7 +111,7 @@ public FieldViewModel create(@NonNull String id, @NonNull String label, @NonNull case USERNAME: return UnsupportedViewModel.create(id, label, mandatory, value, section, editable, description, objectStyle); default: - return EditTextViewModel.create(id, label, mandatory, value, valueTypeHintMap.get(type), 1, type, section, editable, description, fieldRendering, objectStyle, fieldMask); + return EditTextViewModel.create(id, label, mandatory, value, valueTypeHintMap.get(type), 1, type, section, editable, description, fieldRendering, objectStyle, fieldMask, colorByLegend); } } } diff --git a/app/src/main/java/org/dhis2/data/forms/dataentry/fields/edittext/EditTextCustomHolder.java b/app/src/main/java/org/dhis2/data/forms/dataentry/fields/edittext/EditTextCustomHolder.java index 7a22ab8348..cee26e3a4a 100644 --- a/app/src/main/java/org/dhis2/data/forms/dataentry/fields/edittext/EditTextCustomHolder.java +++ b/app/src/main/java/org/dhis2/data/forms/dataentry/fields/edittext/EditTextCustomHolder.java @@ -4,6 +4,7 @@ import android.content.ClipData; import android.content.ClipboardManager; import android.content.Context; +import android.graphics.Color; import android.widget.ArrayAdapter; import android.widget.Toast; @@ -101,6 +102,10 @@ public void update(@NonNull FieldViewModel model) { this.editTextModel = (EditTextViewModel) model; fieldUid = model.uid(); + if (editTextModel.colorByLegend() != null && editTextModel.colorByLegend() != ""){ + binding.customEdittext.setBackgroundColor(Color.parseColor(editTextModel.colorByLegend())); + } + binding.customEdittext.setValueType(editTextModel.valueType()); binding.customEdittext.setObjectStyle(model.objectStyle()); diff --git a/app/src/main/java/org/dhis2/data/forms/dataentry/fields/edittext/EditTextViewModel.java b/app/src/main/java/org/dhis2/data/forms/dataentry/fields/edittext/EditTextViewModel.java index 6f0f40a9a9..a97532629a 100644 --- a/app/src/main/java/org/dhis2/data/forms/dataentry/fields/edittext/EditTextViewModel.java +++ b/app/src/main/java/org/dhis2/data/forms/dataentry/fields/edittext/EditTextViewModel.java @@ -24,15 +24,19 @@ public abstract class EditTextViewModel extends EditTextModel { @Nullable public abstract ValueTypeDeviceRendering fieldRendering(); + @Nullable + public abstract String colorByLegend(); + @NonNull public static EditTextViewModel create(@NonNull String uid, @NonNull String label, @NonNull Boolean mandatory, @Nullable String value, @NonNull String hint, @NonNull Integer lines, @NonNull ValueType valueType, @Nullable String section, @NonNull Boolean editable, @Nullable String description, - @Nullable ValueTypeDeviceRendering fieldRendering, ObjectStyle objectStyle, @Nullable String fieldMask) { + @Nullable ValueTypeDeviceRendering fieldRendering, ObjectStyle objectStyle, @Nullable String fieldMask, + @Nullable String colorByLegend) { return new AutoValue_EditTextViewModel(uid, label, mandatory, value, section, null, editable, null, description, objectStyle, fieldMask,hint, lines, - InputType.TYPE_CLASS_TEXT, valueType, null, null, fieldRendering); + InputType.TYPE_CLASS_TEXT, valueType, null, null, fieldRendering, colorByLegend); } @NonNull @@ -40,7 +44,7 @@ public static EditTextViewModel create(@NonNull String uid, @NonNull String labe public EditTextViewModel withWarning(@NonNull String warning) { return new AutoValue_EditTextViewModel(uid(), label(), mandatory(), value(), programStageSection(), null, editable(), null, - description(), objectStyle(), fieldMask(), hint(), maxLines(), inputType(), valueType(), warning, error(), fieldRendering()); + description(), objectStyle(), fieldMask(), hint(), maxLines(), inputType(), valueType(), warning, error(), fieldRendering(), colorByLegend()); } @NonNull @@ -49,7 +53,7 @@ public EditTextViewModel withError(@NonNull String error) { return new AutoValue_EditTextViewModel(uid(), label(), mandatory(), value(), programStageSection(), null, true, null, description(), objectStyle(), fieldMask(), hint(), maxLines(), inputType(), valueType(), warning(), error, - fieldRendering()); + fieldRendering(), colorByLegend()); } @NonNull @@ -58,7 +62,7 @@ public FieldViewModel setMandatory() { return new AutoValue_EditTextViewModel(uid(), label(), true, value(), programStageSection(), null, editable(), null, description(), objectStyle(), fieldMask(), hint(), maxLines(), InputType.TYPE_CLASS_TEXT, valueType(), warning(), error(), - fieldRendering()); + fieldRendering(), colorByLegend()); } @Nonnull @@ -67,7 +71,7 @@ public FieldViewModel withValue(String data) { return new AutoValue_EditTextViewModel(uid(), label(), mandatory(), data, programStageSection(), null, false, null, description(), objectStyle(), fieldMask(), hint(), maxLines(), InputType.TYPE_CLASS_TEXT, valueType(), warning(), error(), - fieldRendering()); + fieldRendering(), colorByLegend()); } @NonNull @@ -76,5 +80,14 @@ public FieldViewModel withEditMode(boolean isEditable) { return new AutoValue_EditTextViewModel(uid(), label(), mandatory(), value(), programStageSection(), null, isEditable, null, description(), objectStyle(), fieldMask(), hint(), maxLines(), InputType.TYPE_CLASS_TEXT, valueType(), warning(), error(), - fieldRendering()); } + fieldRendering(), colorByLegend()); + } + + @NonNull + public FieldViewModel withColorByLegend(String colorByLegend) { + return new AutoValue_EditTextViewModel(uid(), label(), mandatory(), + value(), programStageSection(), null, editable(), null, + description(), objectStyle(), fieldMask(), hint(), maxLines(), InputType.TYPE_CLASS_TEXT, valueType(), warning(), error(), + fieldRendering(), colorByLegend); + } } diff --git a/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryImpl.java b/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryImpl.java index 80a709e4a2..394bd65322 100644 --- a/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryImpl.java +++ b/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryImpl.java @@ -12,6 +12,7 @@ import org.dhis2.data.forms.dataentry.fields.FieldViewModel; import org.dhis2.data.forms.dataentry.fields.FieldViewModelFactory; import org.dhis2.data.forms.dataentry.fields.FieldViewModelFactoryImpl; +import org.dhis2.data.forms.dataentry.fields.edittext.EditTextViewModel; import org.dhis2.data.forms.dataentry.fields.image.ImageHolder; import org.dhis2.data.forms.dataentry.fields.image.ImageViewModel; import org.dhis2.data.forms.dataentry.fields.option_set.OptionSetViewModel; @@ -33,6 +34,8 @@ import org.hisp.dhis.android.core.enrollment.EnrollmentStatus; import org.hisp.dhis.android.core.event.Event; import org.hisp.dhis.android.core.event.EventStatus; +import org.hisp.dhis.android.core.legendset.Legend; +import org.hisp.dhis.android.core.legendset.LegendSet; import org.hisp.dhis.android.core.maintenance.D2Error; import org.hisp.dhis.android.core.option.Option; import org.hisp.dhis.android.core.option.OptionGroup; @@ -297,7 +300,7 @@ private List checkRenderType(List fieldViewModel fieldViewModel.uid() + "." + option.uid(), option.displayName() + ImageViewModel.NAME_CODE_DELIMITATOR + option.code(), ValueType.TEXT, false, fieldViewModel.optionSet(), fieldViewModel.value(), fieldViewModel.programStageSection(), - fieldViewModel.allowFutureDate(), fieldViewModel.editable() == null ? false : fieldViewModel.editable(), renderingType, fieldViewModel.description(), fieldRendering, options.size(), objectStyle, fieldViewModel.fieldMask())); + fieldViewModel.allowFutureDate(), fieldViewModel.editable() == null ? false : fieldViewModel.editable(), renderingType, fieldViewModel.description(), fieldRendering, options.size(), objectStyle, fieldViewModel.fieldMask() ,null)); } } else if (fieldViewModel instanceof OptionSetViewModel) { @@ -332,8 +335,15 @@ public Flowable> list() { value = friendlyValue; } } + boolean editable = fieldViewModel.editable() != null ? fieldViewModel.editable() : true; - fieldViewModel = fieldViewModel.withValue(value).withEditMode(editable || isEventEditable); + fieldViewModel = fieldViewModel + .withValue(value) + .withEditMode(editable || isEventEditable); + + String colorByLegend = getColorByLegend(value, uid); + fieldViewModel = ((EditTextViewModel)fieldViewModel) + .withColorByLegend(colorByLegend); return fieldViewModel; }).toList().toFlowable() @@ -408,6 +418,8 @@ public Flowable> list() { dataValue = friendlyValue; } + String colorByLegend = getColorByLegend(dataValue, uid); + ProgramStageSectionRenderingType renderingType = programStageSection != null && programStageSection.renderType() != null && programStageSection.renderType().mobile() != null ? programStageSection.renderType().mobile().type() : null; @@ -415,7 +427,7 @@ public Flowable> list() { valueType, mandatory, optionSet, dataValue, programStageSection != null ? programStageSection.uid() : null, allowFurureDates, isEventEditable, - renderingType, description, fieldRendering, optionCount, objectStyle, de.fieldMask()); + renderingType, description, fieldRendering, optionCount, objectStyle, de.fieldMask(), colorByLegend); }) .toList().toFlowable() .map(data -> sectionFields = data) @@ -423,6 +435,25 @@ public Flowable> list() { } } + private String getColorByLegend(String value, String dataElementUid) { + String color = ""; + final DataElement dataElement = d2.dataElementModule().dataElements() + .byUid().eq(dataElementUid) + .withLegendSets() + .one().blockingGet(); + + if (dataElement != null && dataElement.valueType().isNumeric() && + dataElement.legendSets() != null && !dataElement.legendSets().isEmpty()){ + LegendSet legendSet = dataElement.legendSets().get(0); + List legends = d2.legendSetModule().legends().byStartValue().smallerThan( + Double.valueOf(value)).byEndValue().biggerThan(Double.valueOf(value)) + .byLegendSet().eq(legendSet.uid()).blockingGet(); + color = legends.get(0).color(); + } + + return color; + } + @NonNull @Override public Flowable> calculate() { diff --git a/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventSummary/EventSummaryRepositoryImpl.java b/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventSummary/EventSummaryRepositoryImpl.java index 9310503374..d7e7eeb8fd 100644 --- a/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventSummary/EventSummaryRepositoryImpl.java +++ b/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventSummary/EventSummaryRepositoryImpl.java @@ -168,7 +168,7 @@ private FieldViewModel transform(@NonNull ProgramStageDataElement stage, DataEle ValueType.valueOf(valueTypeName), mandatory, optionSet, dataValue, programStageSection, allowFurureDates, eventStatus == EventStatus.ACTIVE, - null, description, fieldRendering, optionCount, objectStyle, dataElement.fieldMask()); + null, description, fieldRendering, optionCount, objectStyle, dataElement.fieldMask(), null); } @NonNull diff --git a/app/src/main/java/org/dhis2/usescases/searchTrackEntity/adapters/FormAdapter.java b/app/src/main/java/org/dhis2/usescases/searchTrackEntity/adapters/FormAdapter.java index 3c82e78bf5..d25a8bffbb 100644 --- a/app/src/main/java/org/dhis2/usescases/searchTrackEntity/adapters/FormAdapter.java +++ b/app/src/main/java/org/dhis2/usescases/searchTrackEntity/adapters/FormAdapter.java @@ -128,7 +128,7 @@ public void onBindViewHolder(@NonNull RecyclerView.ViewHolder holder, int positi case EDITTEXT: viewModel = EditTextViewModel.create(attr.uid(), label, false, queryData.get(attr.uid()), label, 1, attr.valueType(), null, true, - attr.displayDescription(), null, ObjectStyle.builder().build(), attr.fieldMask()); + attr.displayDescription(), null, ObjectStyle.builder().build(), attr.fieldMask(), null); break; case BUTTON: viewModel = FileViewModel.create(attr.uid(), label, false, queryData.get(attr.uid()), null, attr.displayDescription(), ObjectStyle.builder().build()); @@ -166,7 +166,7 @@ public void onBindViewHolder(@NonNull RecyclerView.ViewHolder holder, int positi default: Crashlytics.log("Unsupported viewType " + "source type: " + holder.getItemViewType()); - viewModel = EditTextViewModel.create(attr.uid(), "UNSUPORTED", false, null, "UNSUPPORTED", 1, attr.valueType(), null, false, attr.displayDescription(), null, ObjectStyle.builder().build(), attr.fieldMask()); + viewModel = EditTextViewModel.create(attr.uid(), "UNSUPORTED", false, null, "UNSUPPORTED", 1, attr.valueType(), null, false, attr.displayDescription(), null, ObjectStyle.builder().build(), attr.fieldMask(), null); break; } rows.get(holder.getItemViewType()).onBind(holder, viewModel); diff --git a/app/src/main/java/org/dhis2/utils/customviews/CustomTextView.java b/app/src/main/java/org/dhis2/utils/customviews/CustomTextView.java index 8aa2463750..66bd71e7cf 100644 --- a/app/src/main/java/org/dhis2/utils/customviews/CustomTextView.java +++ b/app/src/main/java/org/dhis2/utils/customviews/CustomTextView.java @@ -3,6 +3,7 @@ import android.annotation.SuppressLint; import android.content.Context; import android.content.res.ColorStateList; +import android.graphics.drawable.ColorDrawable; import android.graphics.drawable.Drawable; import android.text.InputFilter; import android.text.InputType; @@ -17,6 +18,7 @@ import android.widget.ImageView; import android.widget.TextView; +import androidx.annotation.ColorInt; import androidx.core.content.ContextCompat; import androidx.core.content.res.ResourcesCompat; import androidx.databinding.DataBindingUtil; @@ -374,4 +376,8 @@ public void setOnLongActionListener(View.OnLongClickListener listener) { if (!editText.isFocusable()) editText.setOnLongClickListener(listener); } + + public void setBackgroundColor(@ColorInt int color) { + inputLayout.setBackgroundColor(color); + } } diff --git a/app/src/test/java/org/dhis2/usescases/enrollment/EnrollmentPresenterImplTest.kt b/app/src/test/java/org/dhis2/usescases/enrollment/EnrollmentPresenterImplTest.kt index 36f4d2423e..1fceab31be 100644 --- a/app/src/test/java/org/dhis2/usescases/enrollment/EnrollmentPresenterImplTest.kt +++ b/app/src/test/java/org/dhis2/usescases/enrollment/EnrollmentPresenterImplTest.kt @@ -343,6 +343,7 @@ class EnrollmentPresenterImplTest { null, null, ObjectStyle.builder().build(), + null, null ) ) @@ -362,6 +363,7 @@ class EnrollmentPresenterImplTest { null, null, ObjectStyle.builder().build(), + null, null ).withError("error") ) @@ -383,6 +385,7 @@ class EnrollmentPresenterImplTest { null, null, ObjectStyle.builder().build(), + null, null ) diff --git a/app/src/test/java/org/dhis2/utils/RulesUtilsProviderImplTest.kt b/app/src/test/java/org/dhis2/utils/RulesUtilsProviderImplTest.kt index 99b1855b0d..b74b4f03d3 100644 --- a/app/src/test/java/org/dhis2/utils/RulesUtilsProviderImplTest.kt +++ b/app/src/test/java/org/dhis2/utils/RulesUtilsProviderImplTest.kt @@ -81,7 +81,8 @@ class RulesUtilsProviderImplTest { null, null, ObjectStyle.builder().build(), - "" + "", + null ) } From c7ddfeb1d637af0d8cc5a376403e236716ed1d7b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jorge=20Sa=CC=81nchez?= Date: Wed, 1 Jul 2020 12:58:14 +0200 Subject: [PATCH 02/11] Set color by legend only for editText and in non search mode --- app/src/main/assets/paperwork.json | 2 +- .../fields/edittext/EditTextCustomHolder.java | 15 ++++++-- .../EventCaptureRepositoryImpl.java | 34 ++++++++++++------- dhis2-android-sdk | 2 +- 4 files changed, 37 insertions(+), 16 deletions(-) diff --git a/app/src/main/assets/paperwork.json b/app/src/main/assets/paperwork.json index 52580831c3..2d490a5bfd 100644 --- a/app/src/main/assets/paperwork.json +++ b/app/src/main/assets/paperwork.json @@ -1 +1 @@ -{"buildTime":"2020-07-01 07:11","gitSha":"ae505e6d5"} \ No newline at end of file +{"buildTime":"2020-07-01 12:44","gitSha":"822a571c9"} \ No newline at end of file diff --git a/app/src/main/java/org/dhis2/data/forms/dataentry/fields/edittext/EditTextCustomHolder.java b/app/src/main/java/org/dhis2/data/forms/dataentry/fields/edittext/EditTextCustomHolder.java index cee26e3a4a..3127e1a771 100644 --- a/app/src/main/java/org/dhis2/data/forms/dataentry/fields/edittext/EditTextCustomHolder.java +++ b/app/src/main/java/org/dhis2/data/forms/dataentry/fields/edittext/EditTextCustomHolder.java @@ -5,10 +5,12 @@ import android.content.ClipboardManager; import android.content.Context; import android.graphics.Color; +import android.util.Log; import android.widget.ArrayAdapter; import android.widget.Toast; import androidx.annotation.NonNull; +import androidx.core.content.ContextCompat; import androidx.lifecycle.MutableLiveData; import com.google.gson.Gson; @@ -102,8 +104,8 @@ public void update(@NonNull FieldViewModel model) { this.editTextModel = (EditTextViewModel) model; fieldUid = model.uid(); - if (editTextModel.colorByLegend() != null && editTextModel.colorByLegend() != ""){ - binding.customEdittext.setBackgroundColor(Color.parseColor(editTextModel.colorByLegend())); + if (!isSearchMode) { + assignBackgroundColorByLegend(); } binding.customEdittext.setValueType(editTextModel.valueType()); @@ -135,6 +137,15 @@ public void update(@NonNull FieldViewModel model) { setLongClick(); } + private void assignBackgroundColorByLegend() { + if (editTextModel.colorByLegend() != null && editTextModel.colorByLegend() != ""){ + binding.customEdittext.setBackgroundColor(Color.parseColor(editTextModel.colorByLegend())); + } else { + int color = ContextCompat.getColor(binding.customEdittext.getContext(), R.color.form_field_background); + binding.customEdittext.setBackgroundColor(color); + } + } + private void checkAutocompleteRendering() { if (editTextModel.fieldRendering() != null && editTextModel.fieldRendering().type() == ValueTypeRenderingType.AUTOCOMPLETE && diff --git a/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryImpl.java b/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryImpl.java index 394bd65322..0ebc2ea554 100644 --- a/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryImpl.java +++ b/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryImpl.java @@ -341,9 +341,11 @@ public Flowable> list() { .withValue(value) .withEditMode(editable || isEventEditable); - String colorByLegend = getColorByLegend(value, uid); - fieldViewModel = ((EditTextViewModel)fieldViewModel) - .withColorByLegend(colorByLegend); + if (fieldViewModel instanceof EditTextViewModel) { + String colorByLegend = getColorByLegend(value, uid); + fieldViewModel = ((EditTextViewModel)fieldViewModel) + .withColorByLegend(colorByLegend); + } return fieldViewModel; }).toList().toFlowable() @@ -437,21 +439,29 @@ public Flowable> list() { private String getColorByLegend(String value, String dataElementUid) { String color = ""; - final DataElement dataElement = d2.dataElementModule().dataElements() - .byUid().eq(dataElementUid) - .withLegendSets() - .one().blockingGet(); + try{ + + final DataElement dataElement = d2.dataElementModule().dataElements() + .byUid().eq(dataElementUid) + .withLegendSets() + .one().blockingGet(); - if (dataElement != null && dataElement.valueType().isNumeric() && - dataElement.legendSets() != null && !dataElement.legendSets().isEmpty()){ + if (dataElement != null && dataElement.valueType().isNumeric() && + dataElement.legendSets() != null && !dataElement.legendSets().isEmpty()){ LegendSet legendSet = dataElement.legendSets().get(0); List legends = d2.legendSetModule().legends().byStartValue().smallerThan( Double.valueOf(value)).byEndValue().biggerThan(Double.valueOf(value)) .byLegendSet().eq(legendSet.uid()).blockingGet(); - color = legends.get(0).color(); - } - return color; + if (legends.size() > 0) { + color = legends.get(0).color(); + } + } + + return color; + } catch (Exception e){ + return color; + } } @NonNull diff --git a/dhis2-android-sdk b/dhis2-android-sdk index f3e89e26ae..e809249fd3 160000 --- a/dhis2-android-sdk +++ b/dhis2-android-sdk @@ -1 +1 @@ -Subproject commit f3e89e26ae99e61eaa5b20c6c48d568e9e46e10a +Subproject commit e809249fd3699f30af02a0cbc26b8c7b13d35152 From 8f6b5b3827947e36dd607ec375a5d620bc885296 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jorge=20Sa=CC=81nchez?= Date: Thu, 2 Jul 2020 13:55:25 +0200 Subject: [PATCH 03/11] Add to spinners support to assign color by legend --- app/src/main/assets/paperwork.json | 2 +- .../fields/FieldViewModelFactoryImpl.java | 2 +- .../fields/spinner/SpinnerHolder.java | 16 ++++++++++++ .../fields/spinner/SpinnerViewModel.java | 25 +++++++++++++------ .../EventCaptureRepositoryImpl.java | 11 ++++++-- .../adapters/FormAdapter.java | 2 +- .../utils/customviews/OptionSetView.java | 5 ++++ .../eventCapture/EventCapturePresenterTest.kt | 6 +++-- .../utils/optionset/OptionSetPresenterTest.kt | 3 ++- 9 files changed, 57 insertions(+), 15 deletions(-) diff --git a/app/src/main/assets/paperwork.json b/app/src/main/assets/paperwork.json index 2d490a5bfd..d89f5cd3a1 100644 --- a/app/src/main/assets/paperwork.json +++ b/app/src/main/assets/paperwork.json @@ -1 +1 @@ -{"buildTime":"2020-07-01 12:44","gitSha":"822a571c9"} \ No newline at end of file +{"buildTime":"2020-07-02 13:46","gitSha":"c7ddfeb1d"} \ No newline at end of file diff --git a/app/src/main/java/org/dhis2/data/forms/dataentry/fields/FieldViewModelFactoryImpl.java b/app/src/main/java/org/dhis2/data/forms/dataentry/fields/FieldViewModelFactoryImpl.java index 2d205ee16b..78c9989c7f 100644 --- a/app/src/main/java/org/dhis2/data/forms/dataentry/fields/FieldViewModelFactoryImpl.java +++ b/app/src/main/java/org/dhis2/data/forms/dataentry/fields/FieldViewModelFactoryImpl.java @@ -65,7 +65,7 @@ public FieldViewModel create(@NonNull String id, @NonNull String label, @NonNull } else if (fieldRendering != null && type == ValueType.TEXT && optionSetTextRenderings.contains(fieldRendering.type())) { return OptionSetViewModel.create(id, label, mandatory, optionSet, value, section, editable, description, objectStyle, fieldRendering); } else { - return SpinnerViewModel.create(id, label, valueTypeHintMap.get(type), mandatory, optionSet, value, section, editable, description, optionCount, objectStyle); + return SpinnerViewModel.create(id, label, valueTypeHintMap.get(type), mandatory, optionSet, value, section, editable, description, optionCount, objectStyle, colorByLegend); } } else return ImageViewModel.create(id, label, optionSet, value, section, editable, mandatory, description, objectStyle); //transforms option set into image option selector diff --git a/app/src/main/java/org/dhis2/data/forms/dataentry/fields/spinner/SpinnerHolder.java b/app/src/main/java/org/dhis2/data/forms/dataentry/fields/spinner/SpinnerHolder.java index 403b358d68..016ac621c2 100644 --- a/app/src/main/java/org/dhis2/data/forms/dataentry/fields/spinner/SpinnerHolder.java +++ b/app/src/main/java/org/dhis2/data/forms/dataentry/fields/spinner/SpinnerHolder.java @@ -1,10 +1,13 @@ package org.dhis2.data.forms.dataentry.fields.spinner; +import android.graphics.Color; import android.view.View; +import androidx.core.content.ContextCompat; import androidx.fragment.app.FragmentActivity; import androidx.lifecycle.MutableLiveData; +import org.dhis2.R; import org.dhis2.data.forms.dataentry.fields.FormViewHolder; import org.dhis2.data.forms.dataentry.fields.RowAction; import org.dhis2.databinding.FormOptionSetBinding; @@ -58,6 +61,19 @@ public void update(SpinnerViewModel viewModel) { binding.optionSetView.setOnClickListener(this); label = new StringBuilder().append(viewModel.label()); initFieldFocus(); + + if(!isSearchMode){ + assignBackgroundColorByLegend(); + } + } + + private void assignBackgroundColorByLegend() { + if (viewModel.colorByLegend() != null && viewModel.colorByLegend() != ""){ + binding.optionSetView.setBackgroundColor(Color.parseColor(viewModel.colorByLegend())); + } else { + int color = ContextCompat.getColor(binding.optionSetView.getContext(), R.color.form_field_background); + binding.optionSetView.setBackgroundColor(color); + } } @Override diff --git a/app/src/main/java/org/dhis2/data/forms/dataentry/fields/spinner/SpinnerViewModel.java b/app/src/main/java/org/dhis2/data/forms/dataentry/fields/spinner/SpinnerViewModel.java index 37498d75f4..d3e59dd792 100644 --- a/app/src/main/java/org/dhis2/data/forms/dataentry/fields/spinner/SpinnerViewModel.java +++ b/app/src/main/java/org/dhis2/data/forms/dataentry/fields/spinner/SpinnerViewModel.java @@ -1,6 +1,7 @@ package org.dhis2.data.forms.dataentry.fields.spinner; import androidx.annotation.NonNull; +import androidx.annotation.Nullable; import com.google.auto.value.AutoValue; @@ -23,6 +24,9 @@ public abstract class SpinnerViewModel extends FieldViewModel { private List optionGroupsToHide; private List optionGroupsToShow = new ArrayList<>(); + @Nullable + public abstract String colorByLegend(); + @NonNull public abstract String hint(); @@ -33,39 +37,46 @@ public abstract class SpinnerViewModel extends FieldViewModel { public abstract Integer numberOfOptions(); public static SpinnerViewModel create(String id, String label, String hintFilterOptions, Boolean mandatory, - String optionSet, String value, String section, Boolean editable, String description, Integer numberOfOptions, ObjectStyle objectStyle) { - return new AutoValue_SpinnerViewModel(id, label, mandatory, value, section, null, editable, null, null, description, objectStyle, null, hintFilterOptions, optionSet, numberOfOptions == null ? 0 : numberOfOptions); + String optionSet, String value, String section, Boolean editable, String description, Integer numberOfOptions, ObjectStyle objectStyle, String colorByLegend) { + return new AutoValue_SpinnerViewModel(id, label, mandatory, value, section, null, editable, null, null, description, objectStyle, null, colorByLegend, hintFilterOptions, optionSet, numberOfOptions == null ? 0 : numberOfOptions); } @Override public FieldViewModel setMandatory() { - return new AutoValue_SpinnerViewModel(uid(), label(), true, value(), programStageSection(), allowFutureDate(), editable(), warning(), error(), description(), objectStyle(), null, hint(), optionSet(), numberOfOptions()); + return new AutoValue_SpinnerViewModel(uid(), label(), true, value(), programStageSection(), allowFutureDate(), editable(), warning(), error(), description(), objectStyle(), null, colorByLegend(), hint(), optionSet(), numberOfOptions()); } @NonNull @Override public FieldViewModel withError(@NonNull String error) { - return new AutoValue_SpinnerViewModel(uid(), label(), mandatory(), value(), programStageSection(), allowFutureDate(), editable(), warning(), error, description(), objectStyle(), null, hint(), optionSet(), numberOfOptions()); + return new AutoValue_SpinnerViewModel(uid(), label(), mandatory(), value(), programStageSection(), allowFutureDate(), editable(), warning(), error, description(), objectStyle(), null, colorByLegend(), hint(), optionSet(), numberOfOptions()); } @NonNull @Override public FieldViewModel withWarning(@NonNull String warning) { - return new AutoValue_SpinnerViewModel(uid(), label(), mandatory(), value(), programStageSection(), allowFutureDate(), editable(), warning, error(), description(), objectStyle(), null, hint(), optionSet(), numberOfOptions()); + return new AutoValue_SpinnerViewModel(uid(), label(), mandatory(), value(), programStageSection(), allowFutureDate(), editable(), warning, error(), description(), objectStyle(), null, colorByLegend(), hint(), optionSet(), numberOfOptions()); } @Nonnull @Override public FieldViewModel withValue(String data) { - return new AutoValue_SpinnerViewModel(uid(), label(), mandatory(), data, programStageSection(), allowFutureDate(), false, warning(), error(), description(), objectStyle(), null, hint(), optionSet(), numberOfOptions()); + return new AutoValue_SpinnerViewModel(uid(), label(), mandatory(), data, programStageSection(), allowFutureDate(), false, warning(), error(), description(), objectStyle(), null, colorByLegend(), hint(), optionSet(), numberOfOptions()); } @NonNull @Override public FieldViewModel withEditMode(boolean isEditable) { - return new AutoValue_SpinnerViewModel(uid(), label(), mandatory(), value(), programStageSection(), allowFutureDate(), isEditable, warning(), error(), description(), objectStyle(), null, hint(), optionSet(), numberOfOptions()); + return new AutoValue_SpinnerViewModel(uid(), label(), mandatory(), value(), programStageSection(), allowFutureDate(), isEditable, warning(), error(), description(), objectStyle(), null, colorByLegend(), hint(), optionSet(), numberOfOptions()); + } + + @NonNull + public FieldViewModel withColorByLegend(String colorByLegend) { + return new AutoValue_SpinnerViewModel(uid(), label(), mandatory(), value(), programStageSection(), allowFutureDate(), editable(), warning(), error(), description(), objectStyle(), null, colorByLegend, hint(), optionSet(), numberOfOptions()); + } + public void setOptionsToHide(List optionsToHide, List optionsGroupsToHide) { this.optionGroupsToHide = new ArrayList<>(); this.optionsToHide = new ArrayList<>(); diff --git a/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryImpl.java b/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryImpl.java index 0ebc2ea554..e5610601c5 100644 --- a/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryImpl.java +++ b/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryImpl.java @@ -325,8 +325,10 @@ public Flowable> list() { TrackedEntityDataValueObjectRepository valueRepository = d2.trackedEntityModule().trackedEntityDataValues().value(eventUid, uid); String value = null; + String rawValue = null; if (valueRepository.blockingExists()) { value = valueRepository.blockingGet().value(); + rawValue = value; String friendlyValue = ValueExtensionsKt.userFriendlyValue(ValueExtensionsKt.blockingGetValueCheck(valueRepository, d2, uid), d2); if (fieldViewModel instanceof OrgUnitViewModel && !isEmpty(value)) { @@ -342,9 +344,13 @@ public Flowable> list() { .withEditMode(editable || isEventEditable); if (fieldViewModel instanceof EditTextViewModel) { - String colorByLegend = getColorByLegend(value, uid); + String colorByLegend = getColorByLegend(rawValue, uid); fieldViewModel = ((EditTextViewModel)fieldViewModel) .withColorByLegend(colorByLegend); + } else if (fieldViewModel instanceof SpinnerViewModel){ + String colorByLegend = getColorByLegend(rawValue, uid); + fieldViewModel = ((SpinnerViewModel)fieldViewModel) + .withColorByLegend(colorByLegend); } return fieldViewModel; @@ -393,6 +399,7 @@ public Flowable> list() { boolean mandatory = programStageDataElement.compulsory() != null ? programStageDataElement.compulsory() : false; String optionSet = de.optionSetUid(); String dataValue = valueRepository.blockingExists() ? valueRepository.blockingGet().value() : null; + String rawValue = dataValue; String friendlyValue = dataValue != null ? ValueExtensionsKt.userFriendlyValue(ValueExtensionsKt.blockingGetValueCheck(valueRepository, d2, uid), d2) : null; boolean allowFurureDates = programStageDataElement.allowFutureDate() != null ? programStageDataElement.allowFutureDate() : false; @@ -420,7 +427,7 @@ public Flowable> list() { dataValue = friendlyValue; } - String colorByLegend = getColorByLegend(dataValue, uid); + String colorByLegend = getColorByLegend(rawValue, uid); ProgramStageSectionRenderingType renderingType = programStageSection != null && programStageSection.renderType() != null && programStageSection.renderType().mobile() != null ? diff --git a/app/src/main/java/org/dhis2/usescases/searchTrackEntity/adapters/FormAdapter.java b/app/src/main/java/org/dhis2/usescases/searchTrackEntity/adapters/FormAdapter.java index d25a8bffbb..076313e97a 100644 --- a/app/src/main/java/org/dhis2/usescases/searchTrackEntity/adapters/FormAdapter.java +++ b/app/src/main/java/org/dhis2/usescases/searchTrackEntity/adapters/FormAdapter.java @@ -138,7 +138,7 @@ public void onBindViewHolder(@NonNull RecyclerView.ViewHolder holder, int positi viewModel = RadioButtonViewModel.fromRawValue(attr.uid(), label, attr.valueType(), false, queryData.get(attr.uid()), null, true, attr.displayDescription(), ObjectStyle.builder().build(), ValueTypeRenderingType.DEFAULT); break; case SPINNER: - viewModel = SpinnerViewModel.create(attr.uid(), label, "", false, attr.optionSet().uid(), queryData.get(attr.uid()), null, true, attr.displayDescription(), 20, ObjectStyle.builder().build()); + viewModel = SpinnerViewModel.create(attr.uid(), label, "", false, attr.optionSet().uid(), queryData.get(attr.uid()), null, true, attr.displayDescription(), 20, ObjectStyle.builder().build(),null); break; case COORDINATES: viewModel = CoordinateViewModel.create(attr.uid(), label, false, queryData.get(attr.uid()), null, true, attr.displayDescription(), ObjectStyle.builder().build(), FeatureType.POINT); diff --git a/app/src/main/java/org/dhis2/utils/customviews/OptionSetView.java b/app/src/main/java/org/dhis2/utils/customviews/OptionSetView.java index 1e557d69ca..41efee6995 100644 --- a/app/src/main/java/org/dhis2/utils/customviews/OptionSetView.java +++ b/app/src/main/java/org/dhis2/utils/customviews/OptionSetView.java @@ -6,6 +6,7 @@ import android.widget.ImageView; import android.widget.TextView; +import androidx.annotation.ColorInt; import androidx.annotation.Nullable; import androidx.databinding.DataBindingUtil; import androidx.databinding.ObservableField; @@ -192,4 +193,8 @@ public boolean openOptionDialog() { public interface OnSelectedOption { void onSelectedOption(String optionName, String optionCode); } + + public void setBackgroundColor(@ColorInt int color) { + inputLayout.setBackgroundColor(color); + } } diff --git a/app/src/test/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCapturePresenterTest.kt b/app/src/test/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCapturePresenterTest.kt index ef70c41cf0..e90e92b1a9 100644 --- a/app/src/test/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCapturePresenterTest.kt +++ b/app/src/test/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCapturePresenterTest.kt @@ -90,7 +90,8 @@ class EventCapturePresenterTest { false, null, 1, - ObjectStyle.builder().build() + ObjectStyle.builder().build(), + null ) ) @@ -111,7 +112,8 @@ class EventCapturePresenterTest { false, null, 1, - ObjectStyle.builder().build() + ObjectStyle.builder().build(), + null ) ) diff --git a/app/src/test/java/org/dhis2/utils/optionset/OptionSetPresenterTest.kt b/app/src/test/java/org/dhis2/utils/optionset/OptionSetPresenterTest.kt index 90cab649a8..b607deb3f8 100644 --- a/app/src/test/java/org/dhis2/utils/optionset/OptionSetPresenterTest.kt +++ b/app/src/test/java/org/dhis2/utils/optionset/OptionSetPresenterTest.kt @@ -128,7 +128,8 @@ class OptionSetPresenterTest { true, "description", 10, - ObjectStyle.builder().build() + ObjectStyle.builder().build(), + null ) } From bd35e3921ed76ae9fe61f5a1fb5cb0babe7d03c7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jorge=20Sa=CC=81nchez?= Date: Fri, 3 Jul 2020 12:02:23 +0200 Subject: [PATCH 04/11] Fix imports after merge --- app/src/main/assets/paperwork.json | 2 +- .../eventCapture/EventCaptureRepositoryImpl.java | 3 +-- dhis2-android-sdk | 2 +- 3 files changed, 3 insertions(+), 4 deletions(-) diff --git a/app/src/main/assets/paperwork.json b/app/src/main/assets/paperwork.json index d89f5cd3a1..524ded5358 100644 --- a/app/src/main/assets/paperwork.json +++ b/app/src/main/assets/paperwork.json @@ -1 +1 @@ -{"buildTime":"2020-07-02 13:46","gitSha":"c7ddfeb1d"} \ No newline at end of file +{"buildTime":"2020-07-03 11:41","gitSha":"4c312d3c0"} \ No newline at end of file diff --git a/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryImpl.java b/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryImpl.java index 47ef6ea31a..cf0073af13 100644 --- a/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryImpl.java +++ b/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryImpl.java @@ -8,12 +8,11 @@ import org.dhis2.data.forms.FormSectionViewModel; import org.dhis2.data.forms.dataentry.fields.FieldViewModel; import org.dhis2.data.forms.dataentry.fields.FieldViewModelFactory; -import org.dhis2.data.forms.dataentry.fields.FieldViewModelFactoryImpl; import org.dhis2.data.forms.dataentry.fields.edittext.EditTextViewModel; -import org.dhis2.data.forms.dataentry.fields.image.ImageHolder; import org.dhis2.data.forms.dataentry.fields.image.ImageViewModel; import org.dhis2.data.forms.dataentry.fields.optionset.OptionSetViewModel; import org.dhis2.data.forms.dataentry.fields.orgUnit.OrgUnitViewModel; +import org.dhis2.data.forms.dataentry.fields.spinner.SpinnerViewModel; import org.dhis2.utils.DateUtils; import org.dhis2.utils.Result; import org.hisp.dhis.android.core.D2; diff --git a/dhis2-android-sdk b/dhis2-android-sdk index e809249fd3..d1bde91419 160000 --- a/dhis2-android-sdk +++ b/dhis2-android-sdk @@ -1 +1 @@ -Subproject commit e809249fd3699f30af02a0cbc26b8c7b13d35152 +Subproject commit d1bde914193171bcff1b63bf34318cd98271431c From 59fbea36e611e125c107055442e8901ccbebd7e8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jorge=20Sa=CC=81nchez?= Date: Thu, 9 Jul 2020 10:37:59 +0200 Subject: [PATCH 05/11] Retrieve programStage name according to attribute value --- .../eventCaptureRepositoryFunctions.kt | 10 +++++ app/src/main/assets/paperwork.json | 2 +- .../EventCaptureRepositoryImpl.java | 8 +++- .../teidata/TeiDataRepositoryImpl.kt | 12 ++++- .../eventCaptureRepositoryFunctions.kt | 45 +++++++++++++++++++ .../eventCaptureRepositoryFunctions.kt | 10 +++++ dhis2-android-sdk | 2 +- 7 files changed, 83 insertions(+), 6 deletions(-) create mode 100644 app/src/dhis/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/eventCaptureRepositoryFunctions.kt create mode 100644 app/src/psi/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/eventCaptureRepositoryFunctions.kt create mode 100644 app/src/widp/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/eventCaptureRepositoryFunctions.kt diff --git a/app/src/dhis/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/eventCaptureRepositoryFunctions.kt b/app/src/dhis/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/eventCaptureRepositoryFunctions.kt new file mode 100644 index 0000000000..2a664fb32e --- /dev/null +++ b/app/src/dhis/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/eventCaptureRepositoryFunctions.kt @@ -0,0 +1,10 @@ +package org.dhis2.usecases.eventsWithoutRegistration.eventCapture + +import org.hisp.dhis.android.core.D2 + +fun getProgramStageName(d2: D2, eventUid: String): String { + val event = d2.eventModule().events().uid(eventUid).blockingGet() + val programStage = d2.programModule().programStages().uid(event.programStage()).blockingGet() + + return programStage?.displayName() ?: "" +} \ No newline at end of file diff --git a/app/src/main/assets/paperwork.json b/app/src/main/assets/paperwork.json index 7bf9ec48da..c8ea1d6690 100644 --- a/app/src/main/assets/paperwork.json +++ b/app/src/main/assets/paperwork.json @@ -1 +1 @@ -{"buildTime":"2020-07-07 09:52","gitSha":"959f9e840"} \ No newline at end of file +{"buildTime":"2020-07-09 10:33","gitSha":"6ba4c05e0"} \ No newline at end of file diff --git a/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryImpl.java b/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryImpl.java index 1508e78486..6f03ed2632 100644 --- a/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryImpl.java +++ b/app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryImpl.java @@ -47,6 +47,9 @@ import java.util.Date; import java.util.HashMap; import java.util.List; +import java.util.Map; +import java.util.regex.Matcher; +import java.util.regex.Pattern; import io.reactivex.Flowable; import io.reactivex.Observable; @@ -54,6 +57,8 @@ import static android.text.TextUtils.isEmpty; +import static org.dhis2.usecases.eventsWithoutRegistration.eventCapture.EventCaptureRepositoryFunctionsKt.getProgramStageName; + /** * QUADRAM. Created by ppajuelo on 19/11/2018. */ @@ -183,8 +188,7 @@ private boolean getCatComboAccess(Event event) { @Override public Flowable programStageName() { - return Flowable.just(d2.eventModule().events().uid(eventUid).blockingGet()) - .map(event -> d2.programModule().programStages().uid(event.programStage()).blockingGet().displayName()); + return Flowable.just(getProgramStageName(d2, eventUid)); } @Override diff --git a/app/src/main/java/org/dhis2/usescases/teiDashboard/dashboardfragments/teidata/TeiDataRepositoryImpl.kt b/app/src/main/java/org/dhis2/usescases/teiDashboard/dashboardfragments/teidata/TeiDataRepositoryImpl.kt index 818f9ec0c5..fc70b34b51 100644 --- a/app/src/main/java/org/dhis2/usescases/teiDashboard/dashboardfragments/teidata/TeiDataRepositoryImpl.kt +++ b/app/src/main/java/org/dhis2/usescases/teiDashboard/dashboardfragments/teidata/TeiDataRepositoryImpl.kt @@ -3,6 +3,7 @@ package org.dhis2.usescases.teiDashboard.dashboardfragments.teidata import io.reactivex.Single import org.dhis2.Bindings.applyFilters import org.dhis2.Bindings.primaryDate +import org.dhis2.usecases.eventsWithoutRegistration.eventCapture.getProgramStageName import org.dhis2.usescases.teiDashboard.dashboardfragments.teidata.teievents.EventViewModel import org.dhis2.usescases.teiDashboard.dashboardfragments.teidata.teievents.EventViewModelType import org.dhis2.utils.DateUtils @@ -18,6 +19,7 @@ import org.hisp.dhis.android.core.event.EventStatus import org.hisp.dhis.android.core.organisationunit.OrganisationUnit import org.hisp.dhis.android.core.period.DatePeriod import org.hisp.dhis.android.core.program.Program +import org.hisp.dhis.android.core.program.ProgramStage import org.hisp.dhis.android.core.trackedentity.TrackedEntityInstance class TeiDataRepositoryImpl( @@ -150,14 +152,20 @@ class TeiDataRepositoryImpl( event2.primaryDate().compareTo(event1.primaryDate()) } ) + checkEventStatus(eventList).forEach { event -> - val stageUid = d2.programModule().programStages() + + val programStage = d2.programModule().programStages() .uid(event.programStage()) .blockingGet() + + val programStageDisplayName = getProgramStageName(d2, event.uid()) + val editedProgramStage = programStage.toBuilder().displayName(programStageDisplayName).build(); + eventViewModels.add( EventViewModel( EventViewModelType.EVENT, - stageUid, + editedProgramStage, event, 0, null, diff --git a/app/src/psi/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/eventCaptureRepositoryFunctions.kt b/app/src/psi/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/eventCaptureRepositoryFunctions.kt new file mode 100644 index 0000000000..6d4deb0cc1 --- /dev/null +++ b/app/src/psi/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/eventCaptureRepositoryFunctions.kt @@ -0,0 +1,45 @@ +package org.dhis2.usecases.eventsWithoutRegistration.eventCapture + +import org.hisp.dhis.android.core.D2 +import java.util.HashMap + +fun getProgramStageName(d2: D2, eventUid: String): String { + val event = d2.eventModule().events().uid(eventUid).blockingGet() + val programStage = d2.programModule().programStages().uid(event.programStage()).blockingGet() + + //TODO: retrieve attribute name if not exists get programStage + val attValue = "Name:{{MBRvfOpzowH}} Name2:{{MBRvfOpzowH}}" + + return if (attValue.isNotBlank()) { + val getDataElementDisplayName = { uid: String -> + val teValue = d2.trackedEntityModule().trackedEntityDataValues().value(eventUid, uid) + .blockingGet() + + teValue?.value() ?: "" + } + + getProgramStageNameByAttributeValue(attValue, getDataElementDisplayName) + } else { + programStage?.displayName() ?: "" + } +} + +fun getProgramStageNameByAttributeValue( + attValue: String, + getDataElementDisplayName: (uid: String) -> String +): String { + val dataElementsMap: MutableMap = HashMap() + + val matchResults = Regex("\\{\\{(.+?)\\}\\}").findAll(attValue) + + matchResults.forEach { + val uidToken = it.value + if (!dataElementsMap.containsKey(uidToken)) { + val uid = uidToken.substring(2, it.value.length - 2) + dataElementsMap[uidToken] = getDataElementDisplayName(uid) + } + } + + return dataElementsMap.entries.fold(attValue, + { acc: String, (key, value) -> acc.replace(key, value) }) +} \ No newline at end of file diff --git a/app/src/widp/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/eventCaptureRepositoryFunctions.kt b/app/src/widp/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/eventCaptureRepositoryFunctions.kt new file mode 100644 index 0000000000..2a664fb32e --- /dev/null +++ b/app/src/widp/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/eventCaptureRepositoryFunctions.kt @@ -0,0 +1,10 @@ +package org.dhis2.usecases.eventsWithoutRegistration.eventCapture + +import org.hisp.dhis.android.core.D2 + +fun getProgramStageName(d2: D2, eventUid: String): String { + val event = d2.eventModule().events().uid(eventUid).blockingGet() + val programStage = d2.programModule().programStages().uid(event.programStage()).blockingGet() + + return programStage?.displayName() ?: "" +} \ No newline at end of file diff --git a/dhis2-android-sdk b/dhis2-android-sdk index d20dc4b655..3288a65fc3 160000 --- a/dhis2-android-sdk +++ b/dhis2-android-sdk @@ -1 +1 @@ -Subproject commit d20dc4b6554ae9cf40f9204ad623c509dd8c27fa +Subproject commit 3288a65fc3018094ece6d5243555280a5e0ea8d0 From 09008f3289f4910c7ec78c4def1d184316885b54 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jorge=20Sa=CC=81nchez?= Date: Thu, 9 Jul 2020 12:07:09 +0200 Subject: [PATCH 06/11] Add getProgramStageName function to dhisNOSMS flavor --- .../eventCapture/eventCaptureRepositoryFunctions.kt | 10 ++++++++++ 1 file changed, 10 insertions(+) create mode 100644 app/src/dhisNoSMS/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/eventCaptureRepositoryFunctions.kt diff --git a/app/src/dhisNoSMS/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/eventCaptureRepositoryFunctions.kt b/app/src/dhisNoSMS/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/eventCaptureRepositoryFunctions.kt new file mode 100644 index 0000000000..2a664fb32e --- /dev/null +++ b/app/src/dhisNoSMS/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/eventCaptureRepositoryFunctions.kt @@ -0,0 +1,10 @@ +package org.dhis2.usecases.eventsWithoutRegistration.eventCapture + +import org.hisp.dhis.android.core.D2 + +fun getProgramStageName(d2: D2, eventUid: String): String { + val event = d2.eventModule().events().uid(eventUid).blockingGet() + val programStage = d2.programModule().programStages().uid(event.programStage()).blockingGet() + + return programStage?.displayName() ?: "" +} \ No newline at end of file From 90063bad3f64f4d56570cc41c7463ef7750ed436 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jorge=20Sa=CC=81nchez?= Date: Thu, 9 Jul 2020 12:07:54 +0200 Subject: [PATCH 07/11] Fix unit test execution --- app/build.gradle | 4 ---- app/src/main/assets/paperwork.json | 2 +- 2 files changed, 1 insertion(+), 5 deletions(-) diff --git a/app/build.gradle b/app/build.gradle index 7c53b5fe89..f900d67037 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -188,10 +188,6 @@ android { enabled = true } - configurations { - compile.exclude group: "junit", module: "junit" - } - packagingOptions { exclude 'LICENSE.txt' exclude 'META-INF/DEPENDENCIES' diff --git a/app/src/main/assets/paperwork.json b/app/src/main/assets/paperwork.json index c8ea1d6690..7e921894f0 100644 --- a/app/src/main/assets/paperwork.json +++ b/app/src/main/assets/paperwork.json @@ -1 +1 @@ -{"buildTime":"2020-07-09 10:33","gitSha":"6ba4c05e0"} \ No newline at end of file +{"buildTime":"2020-07-09 12:00","gitSha":"59fbea36e"} \ No newline at end of file From 5e1152d73f805c88d021a7c6bf9d89144dfb99de Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jorge=20Sa=CC=81nchez?= Date: Fri, 10 Jul 2020 07:57:06 +0200 Subject: [PATCH 08/11] Search ProgramStageAttributeValue in the database --- app/src/main/assets/paperwork.json | 2 +- .../eventCaptureRepositoryFunctions.kt | 39 +++++++++++++++++-- 2 files changed, 37 insertions(+), 4 deletions(-) diff --git a/app/src/main/assets/paperwork.json b/app/src/main/assets/paperwork.json index 7e921894f0..5db9c5375a 100644 --- a/app/src/main/assets/paperwork.json +++ b/app/src/main/assets/paperwork.json @@ -1 +1 @@ -{"buildTime":"2020-07-09 12:00","gitSha":"59fbea36e"} \ No newline at end of file +{"buildTime":"2020-07-10 07:26","gitSha":"90063bad3"} \ No newline at end of file diff --git a/app/src/psi/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/eventCaptureRepositoryFunctions.kt b/app/src/psi/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/eventCaptureRepositoryFunctions.kt index 6d4deb0cc1..df654a49af 100644 --- a/app/src/psi/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/eventCaptureRepositoryFunctions.kt +++ b/app/src/psi/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/eventCaptureRepositoryFunctions.kt @@ -1,5 +1,6 @@ package org.dhis2.usecases.eventsWithoutRegistration.eventCapture +import org.dhis2.Bindings.userFriendlyValue import org.hisp.dhis.android.core.D2 import java.util.HashMap @@ -7,15 +8,14 @@ fun getProgramStageName(d2: D2, eventUid: String): String { val event = d2.eventModule().events().uid(eventUid).blockingGet() val programStage = d2.programModule().programStages().uid(event.programStage()).blockingGet() - //TODO: retrieve attribute name if not exists get programStage - val attValue = "Name:{{MBRvfOpzowH}} Name2:{{MBRvfOpzowH}}" + val attValue = getProgramStagePatternAttValue(d2,programStage.uid()) return if (attValue.isNotBlank()) { val getDataElementDisplayName = { uid: String -> val teValue = d2.trackedEntityModule().trackedEntityDataValues().value(eventUid, uid) .blockingGet() - teValue?.value() ?: "" + teValue.userFriendlyValue(d2) ?: "" } getProgramStageNameByAttributeValue(attValue, getDataElementDisplayName) @@ -24,6 +24,39 @@ fun getProgramStageName(d2: D2, eventUid: String): String { } } +fun getProgramStagePatternAttValue(d2: D2, programStageUid: String): String { + + val attributeUid = getProgramStagePatternAttributeUid(d2) + + if (attributeUid.isNotBlank()) { + val attributeValueSelect = + "SELECT value FROM ProgramStageAttributeValueLink \n" + + "WHERE attribute = ? AND programStage = ?" + + d2.databaseAdapter().rawQuery(attributeValueSelect, attributeUid, programStageUid) + .use { cursor -> + if (cursor != null && cursor.moveToFirst() && cursor.count > 0) { + return cursor.getString(0) + } + } + } + + return ""; +} + +fun getProgramStagePatternAttributeUid(d2: D2): String { + val attributeCode = "HeaderPattern" + val attributeSelect = "SELECT uid FROM Attribute WHERE code = '${attributeCode}'"; + + d2.databaseAdapter().rawQuery(attributeSelect).use { cursor -> + if (cursor != null && cursor.moveToFirst() && cursor.count > 0) { + return cursor.getString(0) + } + } + + return "" +} + fun getProgramStageNameByAttributeValue( attValue: String, getDataElementDisplayName: (uid: String) -> String From 8fee16e85d3e32149f10871e112955145448f9b5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jorge=20Sa=CC=81nchez?= Date: Mon, 13 Jul 2020 08:44:21 +0200 Subject: [PATCH 09/11] Add getProgramStageNameByAttributeValue tests --- app/src/main/assets/paperwork.json | 2 +- .../usescases/login/LoginPresenterTest.kt | 5 +- .../EventCaptureRepositoryFunctionsTest.kt | 46 +++++++++++++++++++ 3 files changed, 50 insertions(+), 3 deletions(-) create mode 100644 app/src/testPsi/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryFunctionsTest.kt diff --git a/app/src/main/assets/paperwork.json b/app/src/main/assets/paperwork.json index 5db9c5375a..e6c4d2d46f 100644 --- a/app/src/main/assets/paperwork.json +++ b/app/src/main/assets/paperwork.json @@ -1 +1 @@ -{"buildTime":"2020-07-10 07:26","gitSha":"90063bad3"} \ No newline at end of file +{"buildTime":"2020-07-13 08:32","gitSha":"5e1152d73"} \ No newline at end of file diff --git a/app/src/test/java/org/dhis2/usescases/login/LoginPresenterTest.kt b/app/src/test/java/org/dhis2/usescases/login/LoginPresenterTest.kt index 812c976adb..6a5bcb1996 100644 --- a/app/src/test/java/org/dhis2/usescases/login/LoginPresenterTest.kt +++ b/app/src/test/java/org/dhis2/usescases/login/LoginPresenterTest.kt @@ -23,6 +23,7 @@ import org.dhis2.usescases.main.MainActivity import org.dhis2.utils.Constants import org.dhis2.utils.Constants.SECURE_SERVER_URL import org.dhis2.utils.Constants.SECURE_USER_NAME +import org.dhis2.utils.DEFAULT_URL import org.dhis2.utils.TestingCredential import org.dhis2.utils.analytics.AnalyticsHelper import org.dhis2.utils.analytics.CLICK @@ -97,7 +98,7 @@ class LoginPresenterTest { @Test fun `Should set default protocol if server url and username is empty`() { - val protocol = "https://" + val protocol = if (DEFAULT_URL.isEmpty()) "https://" else DEFAULT_URL whenever(userManager.isUserLoggedIn) doReturn Observable.just(false) whenever(preferenceProvider.getBoolean("SessionLocked", false)) doReturn false whenever(view.getDefaultServerProtocol()) doReturn protocol @@ -109,7 +110,7 @@ class LoginPresenterTest { loginPresenter.init(userManager) verify(view).setUrl(protocol) - verify(view, times(2)).getDefaultServerProtocol() + verify(view).getDefaultServerProtocol() verifyNoMoreInteractions(view) } diff --git a/app/src/testPsi/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryFunctionsTest.kt b/app/src/testPsi/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryFunctionsTest.kt new file mode 100644 index 0000000000..541cfb1b93 --- /dev/null +++ b/app/src/testPsi/java/org/dhis2/usecases/eventsWithoutRegistration/eventCapture/EventCaptureRepositoryFunctionsTest.kt @@ -0,0 +1,46 @@ +package org.dhis2.usecases.eventsWithoutRegistration.eventCapture + +import org.junit.Assert +import org.junit.Test + +class EventCaptureRepositoryFunctionsTest { + private val names = mapOf("1" to "name1", "2" to "name2", "3" to "name3") + private val getDataElementDisplayName = { uid: String -> names[uid] ?: "" } + + @Test + fun `Should return expected program stage name replacing data element uid tokens for one data element`() { + val attValue = "Name: {{1}}" + + val result = getProgramStageNameByAttributeValue(attValue, getDataElementDisplayName) + + Assert.assertEquals("Name: name1", result) + } + + @Test + fun `Should return expected program stage name replacing data element uid tokens for two data elements`() { + val attValue = "Name: {{1}} Name2: {{2}}" + + val result = getProgramStageNameByAttributeValue(attValue, getDataElementDisplayName) + + Assert.assertEquals("Name: name1 Name2: name2", result) + } + + @Test + fun `Should return expected program stage name replacing data element uid tokens for three data elements`() { + val attValue = "Name: {{1}} Name2: {{2}} Name3: {{3}}" + + val result = getProgramStageNameByAttributeValue(attValue, getDataElementDisplayName) + + Assert.assertEquals("Name: name1 Name2: name2 Name3: name3", result) + } + + @Test + fun `Should return expected program stage name replacing data element uid tokens for two equal data elements`() { + val attValue = "Name: {{1}} Name2: {{1}}" + + val result = getProgramStageNameByAttributeValue(attValue, getDataElementDisplayName) + + Assert.assertEquals("Name: name1 Name2: name1", result) + } + +} From 40e1a3a4f339c7995c307c788a1ee9acc9595e32 Mon Sep 17 00:00:00 2001 From: Ignacio Foche Perez Date: Fri, 17 Jul 2020 16:46:56 +0200 Subject: [PATCH 10/11] paperwork update --- app/src/main/assets/paperwork.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/src/main/assets/paperwork.json b/app/src/main/assets/paperwork.json index c172ca346c..d6f447d93f 100644 --- a/app/src/main/assets/paperwork.json +++ b/app/src/main/assets/paperwork.json @@ -1 +1 @@ -{"buildTime":"2020-07-07 09:52","gitSha":"959f9e840"} +{"buildTime":"2020-07-17 16:45","gitSha":"effee437f"} \ No newline at end of file From d9cfeeeb4bdb0cbeb1fabd205e232b10acab4aa3 Mon Sep 17 00:00:00 2001 From: Ignacio Foche Perez Date: Fri, 17 Jul 2020 17:36:20 +0200 Subject: [PATCH 11/11] version bumped --- app/build.gradle | 2 +- app/src/main/assets/paperwork.json | 2 +- buildsystem/dependencies.gradle | 4 ++-- dhis2-android-sdk | 2 +- 4 files changed, 5 insertions(+), 5 deletions(-) diff --git a/app/build.gradle b/app/build.gradle index f900d67037..2a7d85ccd9 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -171,7 +171,7 @@ android { applicationId "org.dhis2.psi" dimension "default" versionCode 7 - versionName "2.1.2-psi-fork-1" + versionName "2.1.2-psi-fork-2" } } diff --git a/app/src/main/assets/paperwork.json b/app/src/main/assets/paperwork.json index cc260217c2..b6781e6527 100644 --- a/app/src/main/assets/paperwork.json +++ b/app/src/main/assets/paperwork.json @@ -1 +1 @@ -{"buildTime":"2020-07-17 17:24","gitSha":"8fee16e85"} \ No newline at end of file +{"buildTime":"2020-07-17 17:34","gitSha":"46259d5e6"} \ No newline at end of file diff --git a/buildsystem/dependencies.gradle b/buildsystem/dependencies.gradle index 76bc95563e..965e0ea5f5 100644 --- a/buildsystem/dependencies.gradle +++ b/buildsystem/dependencies.gradle @@ -4,14 +4,14 @@ ext { tools : "28.0.3", minSdk: 19, vCode: 85, - vName: "2.1.2-psi-fork-1" + vName: "2.1.2-psi-fork-2" ] libraries = [ support : "28.0.0", multidex : "2.0.1", constraintlayout : "1.1.3", - dhis2sdk : "1.1.2-psi-fork-1", + dhis2sdk : "1.1.2-psi-fork-2", ruleEngine : "1.0.5.1-SNAPSHOT", atv : "1.2.9", dagger : "2.14.1", diff --git a/dhis2-android-sdk b/dhis2-android-sdk index d5a9803787..93f81a5e2c 160000 --- a/dhis2-android-sdk +++ b/dhis2-android-sdk @@ -1 +1 @@ -Subproject commit d5a980378758733e6af96486cdeea880dec1dcb4 +Subproject commit 93f81a5e2ca95f7f2b262feadad70d35468a34a9