【问题标题】:TextFormField selection handle is overlapping when scrolled offscreen滚动到屏幕外时,TextFormField 选择句柄重叠
【发布时间】:2020-09-09 03:08:44
【问题描述】:

我面临的问题是,当我的 ListView 滚动离开视图时,仍然可以看到文本选择句柄。这是一张供参考的照片,它会更好地解释它:https://imgur.com/a/Lg93cV9

我只在 Android 上测试过,没有 iOS 设备可以测试。

这是我的主要小部件

  @override
  Widget body() {
    return StoreConnector<AppState, Step1IntroViewModel>(
      converter: (store) => Step1IntroViewModel.fromStore(store),
      builder: (context, viewModel) {
        return StepMainTemplate.build(
          this.context,
          child: Column(
            crossAxisAlignment: CrossAxisAlignment.center,
            mainAxisAlignment: MainAxisAlignment.start,
            children: <Widget>[
              _buildImageWidget(),
              Text(
                'Upload image',
                style: TextStyle(
                  color: Colors.red,
                  fontWeight: FontWeight.bold,
                ),
              ),
              Expanded(
                child: ListView(
                  children: <Widget>[
                    StepMainTemplate.title(
                      subtitle: 'Step 1 of 2',
                      title: 'Introduce yourself',
                    ),
                    ProfileForm(
                      key: _profileFormKey,
                      initProfile: viewModel.profileState?.data,
                    ),
                    Container(
                      padding: const EdgeInsets.fromLTRB(0, 40, 0, 20),
                      width: double.infinity,
                      child: RedOneButton.text(
                          text: "Next",
                          function: () {
                            var profile = _profileFormKey.currentState.save();
                            if (profile != null) {
                              viewModel.saveProfile(profile);
                              ExtendedNavigator.ofRouter<Router>()
                                  .pushNamed(Routes.step2Route);
                            }
                          }),
                    ),
                  ],
                ),
              ),
            ],
          ),
        );
      },
    );
  }

这是 ProfileForm

class ProfileForm extends StatefulWidget {
  final Profile initProfile;

  const ProfileForm({Key key, this.initProfile}) : super(key: key);

  @override
  ProfileFormState createState() => ProfileFormState();
}

class ProfileFormState extends State<ProfileForm> {
  final _formKey = GlobalKey<FormState>();

  List<String> genders = ['Male', 'Female'];
  List<String> positions = ['SA', 'PSA', 'PS', 'VPS'];
  String _fullName;
  String _position;
  String _gender;
  String _number;
  String _email;
  String _urlName;

  @override
  void initState() {
    if (widget.initProfile != null) {
      _fullName = widget.initProfile.fullName;
      _position = widget.initProfile.position;
      _gender = widget.initProfile.gender;
      _number = widget.initProfile.phone;
      _email = widget.initProfile.email;
      _urlName = widget.initProfile.urlName;
    }
    super.initState();
  }

  Profile save() {
    if (_formKey.currentState.validate()) {
      _formKey.currentState.save();
      var profile = Profile(
          fullName: _fullName,
          position: _position,
          gender: _gender,
          phone: _number,
          email: _email,
          urlName: _urlName);
      return profile;
    }
    return null;
  }

  @override
  Widget build(BuildContext context) {
    return Padding(
      padding: EdgeInsets.all(12.0),
      child: Form(
          key: _formKey,
          child: Column(
              crossAxisAlignment: CrossAxisAlignment.stretch,
              children: <Widget>[
                ProfileTextFormField(
                  initialValue: _fullName,
                  labelText: 'Full name',
                  hintText: 'Please enter your full name',
                  validator: (value) => Validator.validateFullName(value),
                  textInputAction: TextInputAction.next,
                  textCapitalization: TextCapitalization.words,
                  onSaved: (value) => _fullName = value,
                ),
                ProfileDropDownField(
                    initialValue: _position,
                    labelText: 'Position',
                    hintText: 'Please enter your position',
                    items: positions,
                    onSelected: (value) => _position = value),
                ProfileTextFormField(
                  initialValue: _number,
                  labelText: 'Phone number',
                  hintText: 'Please enter your phone number',
                  validator: (value) => Validator.validatePhone(value),
                  keyboardType: TextInputType.phone,
                  textInputAction: TextInputAction.next,
                  onSaved: (value) => _number = value,
                ),
                ProfileTextFormField(
                  initialValue: _email,
                  labelText: 'Email',
                  hintText: 'Please enter your email',
                  validator: (value) => Validator.validateEmail(value),
                  keyboardType: TextInputType.emailAddress,
                  textInputAction: TextInputAction.next,
                  onSaved: (value) => _email = value,
                  textCapitalization: TextCapitalization.none,
                ),
                ProfileRadioField(
                  initialValue: _gender,
                  labelText: 'Gender',
                  items: genders,
                  onSelected: (value) => _gender = value,
                ),
                ProfileTextFormField(
                  initialValue: _urlName,
                  labelText: 'URL name',
                  hintText: 'Your preferred URL name',
                  textInputAction: TextInputAction.done,
                  onSaved: (value) => _urlName = value,
                  textCapitalization: TextCapitalization.none,
                ),
              ])),
    );
  }
}

也与https://github.com/flutter/flutter/issues/13182有关

【问题讨论】:

    标签: flutter flutter-layout


    【解决方案1】:

    我已经设法通过直接将 TextFormField 直接放在 ListView 中来解决这个问题。这是我让它正常工作的唯一方法。

      @override
      Widget build(BuildContext context) {
        return Form(
            key: _formKey,
            child: ListView(
              padding: const EdgeInsets.all(8.0),
              children: <Widget>[
                widget.header ?? SizedBox.shrink(),
                ..._buildContentList(),
                widget.footer ?? SizedBox.shrink(),
              ],
            ));
      }
    
      List<Widget> _buildContentList() {
        var list = <Widget>[];
        if (widget.hasProfile) list.addAll(_buildProfileFormList());
        if (widget.hasStory) list.addAll(_buildStoryFormList());
        return list;
      }
    
      List<Widget> _buildProfileFormList() {
        return <Widget>[
          ProfileTextFormField(
            initialValue: _profile.fullName,
            labelText: 'Full name',
            hintText: 'Please enter your full name',
            validator: (value) => Validator.validateFullName(value),
            textInputAction: TextInputAction.next,
            textCapitalization: TextCapitalization.words,
            onSaved: (value) => _profile.fullName = value,
          ),
          ProfileDropDownField(
              initialValue: _profile.position,
              labelText: 'Position',
              hintText: 'Please enter your position',
              items: positions,
              onSelected: (value) => _profile.position = value),
          ProfileTextFormField(
            initialValue: _profile.phone,
            labelText: 'Phone number',
            hintText: 'Please enter your phone number',
            validator: (value) => Validator.validatePhone(value),
            keyboardType: TextInputType.phone,
            textInputAction: TextInputAction.next,
            onSaved: (value) => _profile.phone = value,
          ),
          ProfileTextFormField(
            initialValue: _profile.email,
            labelText: 'Email',
            hintText: 'Please enter your email',
            validator: (value) => Validator.validateEmail(value),
            keyboardType: TextInputType.emailAddress,
            textInputAction: TextInputAction.next,
            onSaved: (value) => _profile.email = value,
            textCapitalization: TextCapitalization.none,
          ),
          ProfileRadioField(
            initialValue: _profile.gender,
            labelText: 'Gender',
            items: genders,
            onSelected: (value) => _profile.gender = value,
          ),
          ProfileTextFormField(
            initialValue: _profile.urlName,
            labelText: 'URL name',
            hintText: 'Your preferred URL name',
            textInputAction: TextInputAction.done,
            onSaved: (value) => _profile.urlName = value,
            textCapitalization: TextCapitalization.none,
          ),
        ];
      }
    
      List<Widget> _buildStoryFormList() {
        return <Widget>[
          ProfileTextFormField(
            initialValue: _profile.aboutYourself,
            labelText: '',
            hintText:
                '',
            textInputAction: TextInputAction.next,
            textCapitalization: TextCapitalization.sentences,
            keyboardType: TextInputType.multiline,
            onSaved: (value) => _profile.aboutYourself = value,
            maxLines: 3,
          ),
          ProfileTextFormField(
            initialValue: _profile.sharingMessage,
            labelText: '',
            hintText: '',
            keyboardType: TextInputType.multiline,
            textInputAction: TextInputAction.done,
            maxLength: 300,
            onSaved: (value) => _profile.sharingMessage = value,
            maxLines: 5,
          ),
        ];
      }
    
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2011-06-17
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-04-23
      相关资源
      最近更新 更多