Flutter 컨셉 및 UI 소개

Gun·2023년 9월 21일
0

Flutter

목록 보기
1/25
post-thumbnail

플러터의 위젯은 React에서 영감을 받은 현대적인 프레임워크를 사용하여 구축되었습니다. 핵심 개념은 사용자의 UI를 위젯으로 구축하는 것입니다. 위젯은 현재의 구성과 상태에 따라 그 뷰가 어떻게 보여야 하는지를 설명합니다. 위젯의 상태가 변하면 위젯은 그 설명을 다시 구축하고, 프레임워크는 이전 설명과의 차이점을 비교하여 하나의 상태에서 다음 상태로 전환하기 위해 기본 렌더 트리에서 필요한 최소한의 변경사항을 결정합니다.

- 플러터의 주요 작동 원리와 그 기반이 되는 핵심 개념

import 'package:flutter/material.dart';

void main() {
  // 이 함수는 전달되는 위젯을 애플리케이션의 루트 위젯으로 만들어 준다.
  runApp(
      // Center 위젯은 자식 위젯을 화면의 중앙에 배치하는 위젯
      // Center -> 이 코드에서 Text 위젯이 자식이다.
      Center(
    // Text 위젯은 화면에 문자열을 표시하는 위젯이다.
    // TextDirection - 글자의 방향을 결정합니다.
    // ltr - left to right.
    child: Text('Hello World', textDirection: TextDirection.ltr),
    )
  );
}

이 코드는 "Hello, World"라는 텍스트를 화면의 중앙에 표시하는 Flutter 애플리케이션을 생성

💡 runApp() 함수란

   runApp() 함수는 Flutter 애플리케이션을 시작하는 데 필수적입니다. 
   이 함수를 호출하여 주어진 위젯을 애플리케이션의 루트 위젯으로 설정하고, 
   Flutter 프레임워크와의 초기 연결을 설정합니다.

플러터 기본 위젯 소개

Text
위젯 Text을 사용하면 애플리케이션 내에서 스타일이 지정된 텍스트를 생성할 수 있습니다.

Container
위젯 Container을 사용하면 직사각형의 시각적 요소를 만들 수 있습니다. 컨테이너는 BoxDecoration배경, 테두리, 그림자 등으로 장식될 수 있습니다. Container에는 여백, 안쪽 여백 및 크기에 대한 제약 조건이 적용될 수도 있습니다. 또한, Container행렬을 사용하여 3차원 공간에서 변환될 수 있습니다.

Row,Column
이러한 플렉스 위젯을 사용하면 가로(Row) 및 세로(Column) 방향 모두에서 유연한 레이아웃을 만들 수 있습니다. 이러한 객체의 디자인은 웹의 Flexbox 레이아웃 모델을 기반으로 합니다.

Stack
선형 방향(수평 또는 수직) 대신 Stack위젯을 사용하면 페인트 순서에 따라 위젯을 서로 포개어 배치할 수 있습니다. Positioned그런 다음 a의 하위 항목에 대한 위젯을 사용하여 Stack스택의 위쪽, 오른쪽, 아래쪽 또는 왼쪽 가장자리를 기준으로 위치를 지정할 수 있습니다. 스택은 웹의 절대 위치 지정 레이아웃 모델을 기반으로 합니다.


import 'package:flutter/material.dart';

// 코드의 시작점
void main() {
  runApp(Center(
    child: Container(
      width: 100,
      height: 100,
      color: Colors.lightBlue,
    ),
  ));
}

화면에 렌더링되는 위젯들 중에 자식을 가질 수 있는 위젯이 있고 그 위젯들은 속성 child, children 속성을 가지고 있다.


import 'package:flutter/material.dart';

// 코드의 시작점
void main() {
  runApp(Center(
    child: Container(
      child: const Center(
          child: const Text(
            'Hi Flutter',textDirection: TextDirection.ltr,
          )
      ),
      width: 100,
      height: 100,
      color: Colors.lightBlue,
    ),
  ));
}

MaterialApp vs CupertinoApp

MaterialApp


import 'package:flutter/cupertino.dart'; // iOS
import 'package:flutter/material.dart'; // Google

void main() => runApp(
      MaterialApp(
        home: Scaffold(
          body: Text('Hi ~ Dart And Flutter'),
        ),
      ),
    );

디자인 가이드 라인
Material.io
플러터 Doc
Flutter Document

StatelessWidget - 상태 비저장 위젯

StatelessWidget은 변경할 수 없는 정보를 보유하는 위젯입니다. 이 위젯은 한 번 생성되면 변경되지 않습니다.
이 위젯은 주어진 정보를 기반으로 UI를 구성하지만, 그 자체로 내부 상태를 변경하거나 유지하지 않습니다.


// flutter의 Material 라이브러리
import 'package:flutter/material.dart';

// 애플리케이션의 진입점
void main() {
  //  MyStatelessApp 위젯을 애플리케이션 루트로 설정하고 실행합니다.
  runApp(MyStatelessApp());
}

// 단축키 stl
// StatelessWidget 위젯을 상속해서 MystatelessApp 위젯을 정의합니다.
class MyStatelessApp extends StatelessWidget {
  // 기본 생성자. {} 선택적 key 인자를 상위 클래스로 전달하고 있다.
  const MyStatelessApp({super.key});

  // 이 메서드는 위젯을 반환하고 UI 부분을 렌더링, 빌드합니다.
  
  Widget build(BuildContext context) {
    return MaterialApp(
      // MaterialApp에서 제공하는 레이아웃 구조를 제공합니다.
      home: Scaffold(
        appBar: AppBar(
          title: Text('Widget Example'),
        ),
        body: Center(
          child: Text('Hello My App'),
        ),
      ),
    );
  }
}

StatefulWidget - 변경 가능한 상태를 갖는 위젯

StatefulWidget은 가변적인 상태를 갖는 위젯을 생성하는 데 사용되는 위젯입니다. 사용자와의 상호 작용이나 시간 경과와 같은 요인에 따라 내부 상태가 변할 수 있는 위젯을 만들 때 사용합니다.

상태 관리: StatefulWidget은 내부 상태를 관리하기 위해 별도의 State 객체를 사용합니다. 이 State 객체는 위젯의 생명 주기 동안 상태를 보존합니다.

생명 주기: StatefulWidget은 생성, 업데이트, 제거 등의 생명 주기가 있습니다. 이 생명 주기는 State 객체 내에서 관리됩니다.

변경 알림: 내부 상태가 변경될 때마다 setState() 메서드를 호출하여 Flutter 프레임워크에 알립니다. 그 결과로 build 메서드가 다시 호출되어 UI를 업데이트합니다.


// flutter의 Material 라이브러리
import 'package:flutter/material.dart';

void main() => runApp(MyStatefulApp());

// 단축키 stf
class MyStatefulApp extends StatefulWidget {
  const MyStatefulApp({super.key});

  // createState() 메서드는 State 객체를 생성 합니다.
  // 즉, State 객체가 있다 --> StatefulWidget 이다.
  
  State<MyStatefulApp> createState() => _MyStatefulAppState();
} // end of MyStatefulApp

class _MyStatefulAppState extends State<MyStatefulApp> {
  int _counter = 0;

  // 메서드
  void _incrementCounter() {
    // StatefulWidget과 함께 사용되며 위젯의 상태를 변경하고
    // 화면을 다시 그리게 알려 주는 역할 - build() 실행
    setState(() {
      _counter++;
    });
  }

  
  Widget build(BuildContext context) {
    print('build 메서드 호출 확인');
    return MaterialApp(
      home: Scaffold(
        body: Center(
          child: ElevatedButton(
            onPressed: _incrementCounter,
            child: Text('Count : $_counter'),
          ),
        ),
      ),
    );
  }
} // end of _MyStatefulApp

Handling gestures

대부분의 애플리케이션들은 시스템과의 어떤 형태의 사용자 상호 작용을 포함하고 있습니다. 상호 작용이 있는 애플리케이션을 구축하는 첫 번째 단계는 입력 제스처를 감지하는 것입니다.

Flutter의 제스처(Gestures) 개념

Flutter에서, 제스처는 사용자의 입력 동작(예: 탭, 드래그, 핀치 등)을 감지하는 데 사용되는 도구입니다. Flutter는 위젯 기반의 제스처 인식 시스템을 제공하며, 이를 통해 다양한 사용자 상호 작용을 쉽게 구현할 수 있습니다.

대표적인 제스처 위젯 및 클래스

Tap
GestureDetector 위젯은 단순한 탭 동작을 감지할 수 있습니다.

Double Tap
두 번 탭하는 동작도 GestureDetector로 감지할 수 있습니다.
Drag

사용자의 드래그 동작을 감지합니다.
Pinch

두 손가락으로 확대/축소하는 제스처입니다.

Long Press
사용자가 화면을 길게 누르는 동작을 감지합니다.


import 'package:flutter/material.dart';

void main() => runApp(MyApp());

class MyApp extends StatelessWidget {
  const MyApp({super.key});

  
  Widget build(BuildContext context) {
    return MaterialApp(
      home: MyHomePage(),
    );
  }
} // end of MyApp

class MyHomePage extends StatelessWidget {
  const MyHomePage({super.key});

  
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('Gesture Detector Example'),
      ),
      body: Center(
        // GestureDetector 위젯을 사용하여 다양한 제스처를 감지할 수 있습니다.
        child: GestureDetector(
          onTap: () {
            ScaffoldMessenger.of(context).showSnackBar(
              SnackBar(
                content: Text('Taped'),
              ),
            );
          },
          onLongPress: () {
            ScaffoldMessenger.of(context).showSnackBar(
              SnackBar(
                content: Text('Long Pressed'),
              ),
            );
          },
        ),
      ),
    );
  }
}

Hot RestartHot Reload

  1. Hot Reload:

    • 코드에 변경이 발생했을 때, 변경된 코드만을 즉시 적용하여 앱을 재시작 없이 UI를 업데이트합니다.
    • 상태는 유지되므로, 데이터를 잃지 않고 UI 변경사항을 빠르게 볼 수 있습니다.
    • 주로 UI나 로직의 빠른 반복 개발에 유용합니다.
    • 주의 사항: 몇몇 상황에서는 Hot Reload가 제대로 작동하지 않을 수 있습니다. 예를 들어, 전역 변수의 초기화 코드나 앱의 초기 실행 코드가 변경되었을 때 Hot Reload만으로는 변경 사항이 반영되지 않습니다.
  2. Hot Restart:

    • 앱을 처음부터 다시 시작하여 변경사항을 반영합니다.
    • 앱의 상태를 초기화하므로, 모든 데이터와 상태가 재설정됩니다.
    • 전역 변수나 앱의 초기 실행 코드와 같은 코드 변경사항을 반영하기 위해 사용됩니다.

    주의 사항: Hot Restart를 실행하면 앱의 모든 상태와 데이터가 초기화됩니다. 따라서 특정 상태에서의 테스트나 디버깅을 진행하고 있었다면, 다시 해당 상태로 돌아가기 위한 작업이 필요합니다

0개의 댓글