[flutter] ๐Ÿ“š3์ฃผ์ฐจ ์Šคํ„ฐ๋”” - UI Challenge

seunghyoยท2023๋…„ 11์›” 19์ผ
0

Flutter

๋ชฉ๋ก ๋ณด๊ธฐ
3/5

๐Ÿ“UI Challenge


1. Row, Column class

flutter๋กœ UI ์ž‘์—…์‹œ Row์™€ Column๋กœ ๋ฐฐ์น˜ ๋ ˆ์ด์•„์›ƒ์„ ์žก์„ ์ˆ˜ ์žˆ๋‹ค. Row()์œผ๋กœ ๊ฐ์‹ธ์„œ children ์†์„ฑ์— Widget(Container, Text, SizedBox ๋“ฑ)์„ ๋„ฃ์–ด์ฃผ๋ฉด ๊ฐ€๋กœ๋กœ ์œ„์ ฏ๋“ค์ด ๋ฐฐ์น˜๊ฐ€ ๋œ๋‹ค. Column()์€ ์„ธ๋กœ๋กœ ๋ฐฐ์น˜๊ฐ€ ๋œ๋‹ค.

MainAxisAlignment & CrossAxisAlignment
Row์˜ ๊ฒฝ์šฐ main axis์€ ์ˆ˜ํ‰์œผ๋กœ ์‹คํ–‰๋˜๊ณ  cross axis์€ ์ˆ˜์ง์œผ๋กœ ์‹คํ–‰๋œ๋‹ค. Column์˜ ๊ฒฝ์šฐ main axis์€ ์ˆ˜์ง์œผ๋กœ ์‹คํ–‰๋˜๊ณ  cross axis์€ ์ˆ˜ํ‰์œผ๋กœ ์‹คํ–‰๋œ๋‹ค.

2.center, start, end, spacebetween

  • MainAxisAlignment.center
    • Row() : ๊ฐ€๋กœ์ถ• ๊ธฐ์ค€ ๊ฐ€์šด๋ฐ ์ •๋ ฌ
    • Column() : ์„ธ๋กœ์ถ• ๊ธฐ์ค€ ๊ฐ€์šด๋ฐ ์ •๋ ฌ
  • MainAxisAlignment.start
    • Row(): ๊ฐ€๋กœ์ถ• ๊ธฐ์ค€ ์™ผ์ชฝ ์ •๋ ฌ
    • Column() : ์„ธ๋กœ์ถ• ๊ธฐ์ค€ ์œ„์ชฝ ์ •๋ ฌ
  • MainAxisAlignment.end
    • Row(): ๊ฐ€๋กœ์ถ• ๊ธฐ์ค€ ์˜ค๋ฅธ์ชฝ ์ •๋ ฌ
    • Column() : ์„ธ๋กœ์ถ• ๊ธฐ์ค€ ์•„๋ž˜์ชฝ ์ •๋ ฌ
  • MainAxisAlignment.spaceBetween
    • child widget๋ฅผ ์‹œ์ž‘๊ณผ ๋์— ๋ฐฐ์น˜ํ•˜๊ณ , ์‹œ์ž‘๊ณผ ๋ ์œ„์ ฏ์˜ ์‚ฌ์ด์— ๋‚˜๋จธ์ง€ child widget์„ ๋ฐฐ์น˜ํ•œ๋‹ค. (์‹œ์ž‘๊ณผ ๋ ์‚ฌ์ด์˜ Widget์˜ ๋‚˜๋จธ์ง€ ๊ณต๊ฐ„์€ ๊ท ์ผ)

  • CrossAxisAlignment.start
    • Row(): ๊ฐ€๋กœ์ถ• ๊ธฐ์ค€ ์œ„์ชฝ ์ •๋ ฌ
    • Column() : ์„ธ๋กœ์ถ• ๊ธฐ์ค€ ์™ผ์ชฝ ์ •๋ ฌ
  • CrossAxisAlignment.end
    • Row(): ๊ฐ€๋กœ์ถ• ๊ธฐ์ค€ ์•„๋ž˜ ์ •๋ ฌ
    • Column() : ์„ธ๋กœ์ถ• ๊ธฐ์ค€ ์˜ค๋ฅธ์ชฝ ์ •๋ ฌ

3. Transform class

  • Transform.scale() : ํฌ๊ธฐ๋ฅผ ์กฐ์ ˆ
  • Transform.translate() : ์œ„์น˜๋ฅผ ์กฐ์ ˆ
  • Transform.rotate() : ๊ฐ๋„๋ฅผ ์กฐ์ ˆ

๐Ÿ“ Sample Code

  Transform.scale(
  	scale: 5,
    child: const Icon(
    Icons.euro_rounded,
    color: Colors.white,
    size: 98,
),

4. Reusable Widgets

์œ„์ ฏ์„ ๋ถ„๋ฆฌํ•˜์—ฌ ์žฌ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ๋Š” ์ปดํฌ๋„ŒํŠธ๋กœ ๋งŒ๋“ค ์ˆ˜ ์žˆ๋‹ค.
command + . ์—์„œ Extract Widget ์„ ํƒ ํ›„ ์ด๋ฆ„์„ ์ง€์ •ํ•˜๋ฉด ์ž๋™์œผ๋กœ ํ•ด๋‹น ํŒŒ์ผ ๋‚ด์—์„œ ๋ถ„๋ฆฌ๋ฅผ ํ•ด์ค€๋‹ค.

๐Ÿ“ Sample Code

//button.dart
import 'package:flutter/material.dart';

class Button extends StatelessWidget {
  final String text;
  final Color bgColor;
  final Color textColor;
  const Button({
    super.key,
    required this.text,
    required this.bgColor,
    required this.textColor,
  });
  
  Widget build(BuildContext context) {
    return Container(
      decoration: BoxDecoration(
        color: bgColor,
        borderRadius: BorderRadius.circular(20),
      ),
      child: Padding(
        padding: const EdgeInsets.symmetric(
          vertical: 20,
          horizontal: 50,
        ),
        child: Text(
          text,
          style: TextStyle(
            color: textColor,
            fontSize: 17,
          ),
        ),
      ),
    );
  }
}

๋ฒ„ํŠผ์„ ์žฌ์‚ฌ์šฉํ•˜๊ณ  ์‹ถ๋‹ค๋ฉด ํด๋ž˜์Šค ์ด๋ฆ„๊ณผ ํ•จ๊ป˜ ํ•„์š”ํ•œ ํŒŒ๋ผ๋ฏธํ„ฐ๋ฅผ ์ž‘์„ฑํ•ด์ฃผ๋ฉด ๋œ๋‹ค. ๋ฐ‘์˜ ์ƒ˜ํ”Œ์ฝ”๋“œ๋Š” required๋œ text, bgColor, textColor์„ ์ ์–ด์ฃผ์–ด ์ž‘์„ฑํ•˜์˜€๋‹ค.

๐Ÿ“ Sample Code

 Button(
         text: "Transfer",
         bgColor: Color(0xFFF1B33B),
         textColor: Colors.black,
       ),

5. Developer tools & Widget Inspector

DevTools๋Š” Dart์™€ Flutter๋ฅผ ์œ„ํ•œ ์„ฑ๋Šฅ ๋ฐ ๋””๋ฒ„๊น… ๋„๊ตฌ์ด๋ฉฐ UI ๋ ˆ์ด์•„์›ƒ, ์ƒํƒœ(state)๋ฅผ ์ ๊ฒ€ํ•  ์ˆ˜ ์žˆ๋„๋ก ๋„์™€์ค€๋‹ค. ๊ทธ ์™ธ CPU, Network, Debug Memory issue, ์ฝ”๋“œ ๋ถ„์„, ์ง„๋‹จ ๋“ฑ ์—ฌ๋Ÿฌ ๋ณตํ•ฉ์ ์ธ ๊ธฐ๋Šฅ๋“ค์„ ์ œ๊ณตํ•œ๋‹ค. ์ฃผ์˜ํ•  ์ ์€ ์•ฑ์„ ๊ตฌ๋™ํ•œ ์ƒํƒœ์—ฌ์•ผ ํ•œ๋‹ค๋Š” ๊ฒƒ์ด๋‹ค. ๊ทธ ์ดํ›„ ํ•ด๋‹น ํ™”๋ฉด์— ์žˆ๋Š” open devTools๋ฅผ ์‹คํ–‰ํ•  ์ˆ˜ ์žˆ๋‹ค.

๊ทธ ์ค‘ widget Inspector๋ฅผ ์‹คํ–‰ํ•˜๋ฉด ์œ„์ ฏ ํŠธ๋ฆฌ๋ฅผ ์‹œ๊ฐํ™”ํ•˜๊ณ  ํƒ์ƒ‰ํ•  ์ˆ˜ ์žˆ๋‹ค.

6. Code Challenge(#3.9)

class CurrencyCard extends StatelessWidget {
  final String name, code, amount;
  final IconData icon;
  final bool isInverted;
  final _blackColor = const Color(0xFF1F2123);
  final double offset; //์ƒˆ ๋ณ€์ˆ˜ ์„ ์–ธ

  const CurrencyCard({
    super.key,
    required this.name,
    required this.code,
    required this.amount,
    required this.icon,
    required this.isInverted,
    required this.offset, 
  });
    Widget build(BuildContext context) {
    return Transform.translate(
      offset: Offset(0, offset), //offset ์„ค์ •
      child: Container(
        clipBehavior: Clip.hardEdge,
  //(์ƒ๋žต)

์ฐธ๊ณ ์ž๋ฃŒ
https://nomadcoders.co/flutter-for-beginners/lectures/4139
https://docs.flutter.dev/ui/layout
https://docs.flutter.dev/tools/devtools/inspector
https://www.w3.org/TR/css-align-3/
https://css-tricks.com/almanac/properties/j/justify-content/

0๊ฐœ์˜ ๋Œ“๊ธ€