Spec воссоздается при смене видимости софт-клавиатуры

Я использую Litho (0,8).

У меня есть Spec, который создает Recycler, который может содержать несколько компонентов разных типов (текст, флажки, переключатели и т. Д.).

Вот основная спецификация:

@LayoutSpec
public class LithoActivitySpec {

    @OnCreateLayout
    static ComponentLayout onCreateLayout(final ComponentContext c, @Prop FormDescription formDescription,
                                          @Prop FormFieldSpec.FormFieldListener listener,
                                          @Prop ButtonSpec.ButtonClickListener buttonListener) {

        final RecyclerBinder recyclerBinder = new RecyclerBinder.Builder()
                .layoutInfo(new LinearLayoutInfo(c, OrientationHelper.VERTICAL, false))
                .build(c);

        final Component recycler = Recycler.create(c)
                .binder(recyclerBinder)
                .build();

        bindDescriptionToRecycler(c, recyclerBinder, formDescription, listener);
        return Column.create(c)
                .child(Button.create(c)
                        .text("validate")
                        .listener(buttonListener))
                .child(recycler)
                .build();
    }

    private static void bindDescriptionToRecycler(ComponentContext c, RecyclerBinder recyclerBinder,
                                                  FormDescription formDescription,
                                                  FormFieldSpec.FormFieldListener listener) {
        List<RenderInfo> renderInfos = new ArrayList<>();
        for (ElementValue elementValue : formDescription.elementValues) {
            ElementValueType elementValueType = elementValue.getElementValueType();
            renderInfos.add(ComponentRenderInfo.create().component(
                    FormField.create(c)
                            .text(elementValueType.getName())
                            .dataType(elementValueType.getElementValueDataType())
                            .elementValueTypeId(elementValueType.getId())
                            .listener(listener)
                            .build())
                    .build()
            );
        }
        recyclerBinder.insertRangeAt(0, renderInfos);
    }
...
}

И вот спецификация, которая будет строить правильный компонент в зависимости от типа данных:

@LayoutSpec
public class FormFieldSpec {

    public static final int TEXT_SIZE = 16;

    @OnCreateLayout
    static ComponentLayout onCreateLayout(ComponentContext c,
                                          @Prop String text,
                                          @Prop ElementValueDataType dataType,
                                          @Prop String elementValueTypeId,
                                          @Prop FormFieldListener listener) {
        return Row.create(c)
                .paddingDip(YogaEdge.ALL, 16)
                .child(Text.create(c)
                        .text(text)
                        .verticalGravity(VerticalGravity.CENTER)
                        .textColor(ContextCompat.getColor(c, android.R.color.tab_indicator_text))
                        .textStyle(Typeface.BOLD)
                        .textSizeSp(TEXT_SIZE)
                        .isSingleLine(false)
                        .widthPercent(33.0f))
                .child(getValueComponentLayout(c, dataType, elementValueTypeId, listener))
                .build();
    }

    private static ComponentLayout getValueComponentLayout(ComponentContext c,
                                                           ElementValueDataType dataType,
                                                           String elementValueTypeId,
                                                           FormFieldListener listener) {
        Component.Builder builder;
        switch (dataType.getType()) {
            case DATE: builder = FormFieldDate.create(c)
                    .elementValueTypeId(elementValueTypeId)
                    .allowFuture(((DateDataType) dataType).isFuturePossible())
                    .withTime(((DateDataType) dataType).isWithTime())
                    .listener(listener);
                break;
            case RADIO_BOOLEAN: builder = FormFieldRadioBoolean.create(c)
                    .elementValueTypeId(elementValueTypeId)
                    .listener(listener)
                    .valueTrue(((RadioBooleanDataType) dataType).getValueTrue())
                    .valueFalse(((RadioBooleanDataType) dataType).getValueFalse());
                break;
            case CHECK_BOOLEAN: builder =  FormFieldCheckBoolean.create(c)
                    .elementValueTypeId(elementValueTypeId)
                    .listener(listener)
                    .valueTrue(((CheckBooleanDataType) dataType).getValueTrue())
                    .valueFalse(((CheckBooleanDataType) dataType).getValueFalse());
                break;
            case STRING_LIST: builder = FormFieldVdoList.create(c)
                    .elementValueTypeId(elementValueTypeId)
                    .listener(listener)
                    .allowCustomValues(((StringListDataType) dataType).allowCustomValues())
                    .rootOption(((StringListDataType) dataType).getRootOption());
                break;
            default: builder = FormFieldString.create(c)
                    .elementValueTypeId(elementValueTypeId)
                    .listener(listener);
        }
        return builder.buildWithLayout();
    }
...
}

Так что, если у меня есть Recycler, который выглядит примерно так:

  • Дата
  • Радио
  • строка
  • Проверьте
  • строка

Каждый раз, когда я открываю или скрываю клавиатуру, все мои поля становились пустыми. Я установил точку останова на LithoActivitySpec#onCreateLayout() и я видел, что каждый раз, когда клавиатура меняет свою видимость, вызывается этот метод.

Это ошибка или что-то я не так делаю на моей стороне? Это их onSaveInstanceStateили что-то похожее на это?

Спасибо.

0 ответов

Другие вопросы по тегам