QuickBirdEng / survey_kit

Flutter library to create beautiful surveys (aligned with ResearchKit on iOS)
MIT License
127 stars 97 forks source link

Custom Step / Custom Slider #131

Open pmagnuson opened 1 year ago

pmagnuson commented 1 year ago

I am finding it quite difficult to navigate the documentation of CustomResult & CustomStep.

My goal is to create a custom Slider instead of ScaledAnswerFormat.

Any examples would be greatly appreciated.

pmagnuson commented 1 year ago

I have defined the following as a custom step in a NavigableTask

// avoid collisions on Step class
import 'package:survey_kit/survey_kit.dart' as k;

class CustomScaleStep extends k.Step {
  final sliderKey = GlobalKey<SliderTextState>();
  @override
  Widget createView({required k.QuestionResult? questionResult}) {
    return k.StepView(
        step: k.QuestionStep(
            showAppBar: false,
            answerFormat: const k.IntegerAnswerFormat(
              defaultValue: 5,
            )),
        title: const Text('title'),
        child: SliderText(key: sliderKey),  // custom component
        resultFunction: () => k.IntegerQuestionResult(
            id: k.Identifier(id: 'identifier'),
            startDate: DateTime.now(),
            endDate: DateTime.now(),
            valueIdentifier: 'valueIdentifier',
            result: sliderKey.currentState!.sliderCurrentValue.toInt()));
  }

  @override
  Map<String, dynamic> toJson() {
    return {};
  }
}

The showAppBar: false, seems to be ignored.

pmagnuson commented 1 year ago

With the following custom Step:


// avoid collision with material Step
import 'package:survey_kit/survey_kit.dart' as sk;

class CustomScaleStep extends sk.Step {
  final sliderKey = GlobalKey<SliderTextState>();

  @override
  Widget createView({required sk.QuestionResult? questionResult}) {
    return sk.StepView(
        step: sk.QuestionStep(
            // showAppBar: false,
            answerFormat: const sk.IntegerAnswerFormat(
          defaultValue: 5,
        )),
        title: const Text('title'),
        child: SliderText(key: sliderKey),
        resultFunction: () {
          print('result ${sliderKey.currentState!.sliderCurrentValue.toInt()}');
          return sk.IntegerQuestionResult(
            id: sk.StepIdentifier(),
            startDate: DateTime.now(),
            endDate: DateTime.now(),
            valueIdentifier:
                sliderKey.currentState!.sliderCurrentValue.toInt().toString(),
            result: sliderKey.currentState!.sliderCurrentValue.toInt(),
          );
        });
  }

  @override
  Map<String, dynamic> toJson() {
    return {};
  }
}

and in the enclosing task, this navigation rule is added:


    task.addNavigationRule(
      forTriggerStepIdentifier: task.steps[1].stepIdentifier,
      navigationRule:
          sk.ConditionalNavigationRule(resultToStepIdentifierMapper: (input) {
        if ((input == '1') || (input == '2')) {
          return null;
        }
        return task.steps[0].stepIdentifier;
      }),
    );

in the ConditionalNavigationRule the input variable reflects the value of valueIdentifier in the CustomScaleStep.

It seems that the choice of naming between valueIdentifier and result could be improved in the resultFunction. It would be more intuitive if input reflected the result parameter.

pmagnuson commented 1 year ago

I am also interested in building a CustomStep that will play a video and then move to the next step. Is there a way to trigger the Next button on an arbitrary event? I would be best to disable the Next button or not show until the event has occurred. Thanks!

adar2378 commented 10 months ago

@pmagnuson Hi, are you using CustomStep via json? How are you able to add the json parser for the custom step in survey_kit?

pmagnuson commented 10 months ago

@adar2378 I am no longer using this library.