seong

flutter ViewInset영역 처리 하기 - 키보드, FormField영역 겹치지 않게 하기 본문

Flutter/Flutter

flutter ViewInset영역 처리 하기 - 키보드, FormField영역 겹치지 않게 하기

hyeonseong 2022. 12. 1. 16:16

1. 기존의 StlessWidget -> StatefulWidget로 바꾸어준다.

2. ScrollController를 선언해준다. 

ScrollController란? 스크롤이 가능한 위젯을 제어해준다.

3. 해당 위젯의 가장 하단에 움직임을 실행시켜줄 함수 작성

4. 필요한 부분에 해당 함수를 넘겨준다.

5. 받는 쪽에선 생성자로 받아준다 

- Type : Function

6. 실행 시점은 TextFormField를 눌렀을때 이므로 onTap으로 누르면 메서드 실행

 

전체 코드1

import 'package:finalproject_front/constants.dart';
import 'package:finalproject_front/pages/sign/components/custom_text_form_field.dart';
import 'package:finalproject_front/pages/user/user_detail/components/image_box.dart';
import 'package:finalproject_front/pages/user/user_profile_insert/components/career_select_button.dart';
import 'package:finalproject_front/pages/user/user_profile_insert/components/profile_career_list.dart';
import 'package:finalproject_front/pages/user/user_profile_insert/components/profile_certificate.dart';
import 'package:finalproject_front/pages/user/user_profile_insert/components/profile_education.dart';
import 'package:finalproject_front/pages/user/user_profile_insert/components/profile_id.dart';
import 'package:finalproject_front/pages/user/user_profile_insert/components/profile_image.dart';
import 'package:finalproject_front/pages/user/user_profile_insert/components/profile_insert_button.dart';
import 'package:finalproject_front/pages/user/user_profile_insert/components/profile_intro.dart';
import 'package:finalproject_front/pages/user/user_profile_insert/components/profile_place.dart';
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';

class UserProfileInsertPage extends StatefulWidget {
  const UserProfileInsertPage({super.key});

  @override
  State<UserProfileInsertPage> createState() => _UserProfileInsertPageState();
}

class _UserProfileInsertPageState extends State<UserProfileInsertPage> {
  late ScrollController
      scrollController; // ScrollerController은 non-null이다, late를 선언해 나중에 초기화.

  @override
  void initState() {
    super.initState();
    scrollController = new ScrollController();
  }

  @override
  Widget build(BuildContext context) {
    Size size = MediaQuery.of(context).size;
    return Scaffold(
      appBar: _buildAppbar(context),
      body: SingleChildScrollView(
        child: Padding(
          padding: const EdgeInsets.all(20.0),
          child: Column(
            crossAxisAlignment: CrossAxisAlignment.start,
            children: [
              ProfileImage(imagePath: "assets/picture.jpg"),
              SizedBox(height: 20),
              ProfileId(),
              SizedBox(height: 20),
              ProfileIntro(scrollAnimate),
              SizedBox(height: 20),
              ProfilePlace(scrollAnimate),
              SizedBox(height: 20),
              ProfileEducation(scrollAnimate),
              SizedBox(height: 20),
              ProfileCertificate(scrollAnimate),
              SizedBox(height: 20),
              ProfileCareer(),
              SizedBox(height: 20),
              ProfileCareerList(scrollAnimate),
              SizedBox(height: 20),
              ProfileInsertButton()
            ],
          ),
        ),
      ),
    );
  }

  AppBar _buildAppbar(BuildContext context) {
    return AppBar(
      elevation: 1,
      centerTitle: true,
      title: Text(
        "프로필 등록/수정",
        style: TextStyle(color: Colors.black, fontWeight: FontWeight.bold),
      ),
      leading: IconButton(
          icon: Icon(
            CupertinoIcons.back,
            color: Colors.black,
            size: 30,
          ),
          onPressed: () {
            Navigator.pop(context);
          }),
    );
  }

  void scrollAnimate() {
    Future.delayed(Duration(milliseconds: 600), () {
      //0.6초 이후 키보드 올라옴
      // ViewInsets은 현재 페이지에서 내가 컨트롤 할 수 없는 영역을 뜻함,
      // bottom은 키보드가 아래에서 올라오기 때문
      scrollController.animateTo(MediaQuery.of(context).viewInsets.bottom,
          duration: Duration(microseconds: 100), // 0.1초 이후 field가 올라간다.
          curve: Curves.easeIn); //Curves - 올라갈때 애니메이션
    });
  }
}

 

전체 코드2

import 'package:finalproject_front/constants.dart';
import 'package:flutter/material.dart';

class ProfilePlace extends StatelessWidget {
  final Function scrollAnimate;
  const ProfilePlace(
    this.scrollAnimate, {
    Key? key,
  }) : super(key: key);

  @override
  Widget build(BuildContext context) {
    return Container(
      child: Column(
        children: [
          Align(
            alignment: Alignment.centerLeft,
            child: Text(
              "지역을 작성해주세요.",
              style: TextStyle(fontSize: 18, fontWeight: FontWeight.bold),
            ),
          ),
          SizedBox(height: 10),
          TextFormField(
            onTap: (() {
              scrollAnimate;
            }),
            decoration: InputDecoration(
              hintText: "예) 부산, 서울, 경기도",
              hintStyle: TextStyle(
                fontSize: 14,
                fontWeight: FontWeight.normal,
                color: gSubTextColor,
              ),
              //3. 기본 textFormfield 디자인 - enabledBorder
              enabledBorder: OutlineInputBorder(
                borderSide: BorderSide(color: gBorderColor, width: 3.0),
                borderRadius: BorderRadius.circular(15),
              ),
              //마우스 올리고 난 후 스타일
              focusedBorder: OutlineInputBorder(
                borderSide: BorderSide(color: gBorderColor, width: 3.0),
                borderRadius: BorderRadius.circular(15),
              ),
            ),
          ),
        ],
      ),
    );
  }
}

'Flutter > Flutter' 카테고리의 다른 글

Riverpod 기본 세팅 및 테스트 코드 작성  (0) 2022.12.07
Flutter selectCheckbox  (0) 2022.12.05
Flutter - Text.rich  (0) 2022.11.26
InkWell 위젯 - 버튼화 시키기  (0) 2022.11.25
Container의 decoration으로 테두리 주기  (1) 2022.11.25